小编Edm*_*und的帖子

只读内存访问的线程安全性

我在C中实现了Barnes-Hut重力算法如下:

  1. 建立一群星团.
  2. 对于每颗恒星,遍历树并应用每个适用节点的重力.
  3. 更新恒星速度和位置.

阶段2是最昂贵的阶段,因此通过划分星组来并行实施.例如,有1000颗星和2个线程,我有一个线程处理前500颗星,第二个线程处理第二个500颗.

在实践中,这是有效的:与非线程版本相比,它在双核机器上使用两个线程将计算速度提高了大约30%.此外,它产生与原始非线程版本相同的数值结果.

我担心的是两个线程同时访问相同的资源(即树).我没有向线程工作者添加任何同步,因此他们可能会尝试在某个时刻从同一位置读取.虽然访问树是严格只读的,但我并不是100%确定它是安全的.它在我测试它时起作用,但我知道这不能保证正确性!

问题

  • 我是否需要为每个线程制作树的私有副本?
  • 即使它是安全的,是否存在从多个线程访问相同内存的性能问题?

更新好奇的基准测试结果:

机器:Intel Atom CPU N270 @ 1.60GHz,cpu MHz 800,高速缓存大小512 KB

Threads      real      user      sys
      0    69.056    67.324    1.720
      1    76.821    66.268    5.296
      2    50.272    63.608   10.585
      3    55.510    55.907   13.169
      4    49.789    43.291   29.838
      5    54.245    41.423   31.094
Run Code Online (Sandbox Code Playgroud)

0表示根本没有线程; 1及以上意味着产生许多工作线程和主线程等待它们.我不希望超过2个线程的任何改进,因为它完全受CPU限制,而且有多少个核心.有趣的是,奇数个线程比偶数更差.

看着sys它显然是制作线程的成本.目前它正在为每个帧创建线程(因此N*1000线程创建).这很容易编程(今天早上我在火车上的15分钟).我需要考虑一下如何重用线程......

更新#2我使用了一个线程池,与两个障碍同步.与每帧重新创建线程相比,这没有明显的性能优势.

c pthreads thread-safety

4
推荐指数
1
解决办法
2786
查看次数

跨多个模块定义谓词的各个部分

我正在尝试编写一个move/3处理几种术语的谓词,每种术语都在一个单独的文件中定义.我正在尝试使用模块,因为这些文件包含应该适当命名的其他谓词.

所以,我创建了一个cat.prolog包含内容的模块:

:- module(cat, [move/3]).
:- multifile(move/3).

move(cat(C), P, cat(C2)) :-
   ...
Run Code Online (Sandbox Code Playgroud)

同样的dog.prolog.

main.prolog与:

:- use_module(['cat.prolog'], [move/3]).
:- use_module(['dog.prolog'], [move/3]).

(various predicates that use move/3 and expecting the clauses from all imported modules to be applicable.)
Run Code Online (Sandbox Code Playgroud)

试图在SWI-Prolog中运行它:

?- ['main.prolog'].
%  cat.prolog compiled into cat 0.00 sec, 4,800 bytes
ERROR: Cannot import dog:move/3 into module user: already imported from cat
Warning: /home/edmund/main.prolog:2:
        Goal (directive) failed: user:use_module([dog.prolog],[move/3])
% main.prolog compiled 0.00 sec, 10,176 bytes …
Run Code Online (Sandbox Code Playgroud)

module prolog swi-prolog

4
推荐指数
1
解决办法
809
查看次数

从一系列解析器组合器构造长度为n的元组

  • 题.有没有办法定义一个运算符,使得由该运算符分隔的一系列值产生一个扁平元组?

我一直在努力找到一个简明扼要的措辞,所以请继续阅读详细信息和示例......

描述

我正在为Parsec编写一些帮助操作符,从以下开始:

(<@) :: GenParser tok st a -> (a -> b) -> GenParser tok st b
p <@ f = do {
    x <- p ;
    return (f x)
}

(<>) :: GenParser tok st a -> GenParser tok st b -> GenParser tok st (a, b)
p <> q = do {
    x <- p ;
    y <- q ;
    return (x, y)
 }
Run Code Online (Sandbox Code Playgroud)

这些工作如下:

parseTest ((many upper) <@ length) "HELLO"
5

parseTest (many upper) …
Run Code Online (Sandbox Code Playgroud)

haskell parser-combinators

3
推荐指数
1
解决办法
245
查看次数

使用make生成bison语法

在使用make和的项目中bison,我很难指定编译的语法grammar.tab.c依赖于语法输入grammar.y,每个目标文件依赖于相应的源文件(包括grammar.tab.o),并且可执行文件依赖于所有目标文件.

问题是make当grammar.tab.c尚不存在时运行意味着没有尝试构建它,并且当构建可执行文件时,该yyparse函数丢失.

Makefile是:

CFLAGS = -g -Wall
YACC = bison -d -r all
OBJ=$(patsubst %.c, %.o, $(wildcard *.c))
HEADERS=grammar.tab.h hex.h compiler.h types.h

all: grammar.tab.h c

clean:
    rm -f $(OBJ) *.tab.c *.tab.h c c.exe *.output

c: $(OBJ)
    $(CC) -o $@ $(OBJ) $(CFLAGS)

grammar.tab.c: grammar.y
    $(YACC) grammar.y

grammar.tab.h: grammar.y
    $(YACC) grammar.y

%.o: %.c $(HEADERS)
    $(CC) -c $< $(CFLAGS)
Run Code Online (Sandbox Code Playgroud)

如果我改变它:

OBJ=$(patsubst %.c, %.o, $(wildcard *.c)) grammar.tab.o
Run Code Online (Sandbox Code Playgroud)

然后它将构建已编译的语法(如果它尚不存在).但是如果它已经存在,那么在构建可执行文件时,会出现 …

makefile compilation bison

2
推荐指数
1
解决办法
3399
查看次数

Postgres订购不一致

我有一个问题,即postgres有序的结果不是一致的.我按多个字段排序:ORDER BY categories.position ASC,photos.display_priority

我注意到这一点,因为当您浏览网站时,结果是分页的.我发现了一个从第1页到第2页的情况,在第2页的顶部,我看到了第1页底部附近的照片.

这是我的第1页查询:

SELECT "photos".*
FROM "photos"
    INNER JOIN "categories" ON "categories"."id" = "photos"."category_id"
WHERE "photos"."category_id" IN (221, 633, 377, 216, 634)
    AND (photos.caption IS NOT NULL
        AND photos.category_id IS NOT NULL
        AND photos.rights IS NOT NULL
        AND photos.deleted IS NULL)
ORDER BY categories.position ASC, photos.display_priority DESC
LIMIT 25 OFFSET 0;
Run Code Online (Sandbox Code Playgroud)

我的第2页查询:

SELECT "photos".*
FROM "photos"
    INNER JOIN "categories" ON "categories"."id" = "photos"."category_id"
WHERE "photos"."category_id" IN (221, 633, 377, 216, 634)
    AND (photos.caption IS NOT NULL
        AND …
Run Code Online (Sandbox Code Playgroud)

postgresql

1
推荐指数
1
解决办法
635
查看次数