提问人:Peheje 提问时间:10/24/2017 更新时间:10/24/2017 访问量:1219
Nim:具有变异状态的并行环路
Nim: Parallel loop with mutating state
问:
我是尼姆语的新手。我想通过实现一个简单的遗传算法来学习它,通过将工作分配给 CPU 内核来演化字符串(整数数组 atm):
https://github.com/peheje/nim_genetic
我已经成功地并行创建了“代理”,但无法调用必须改变传递状态的函数“life”:
...
type
Agent* = ref object
data*: seq[int]
fitness*: float
...
var pool: seq[Agent] = newAgentsParallel(POPULATION_SIZE)
# Run generations
for gen in 0..<N_GENERATIONS:
let wheel = createWheel(pool)
let partitions: seq[seq[Agent]] = partition(pool, N_THREADS)
parallel:
for part in partitions:
echo "spawning"
spawn life(part, pool, wheel)
pool = createPool(pool, wheel)
...
proc life(part: seq[Agent], pool: seq[Agent], wheel: seq[float]) =
for a in part:
if random(1.0) < CROSSOVER_PROP:
a.crossover(pool, wheel)
if random(1.0) < MUTATE_PROP:
a.mutate()
a.calcFitness()
echo "life done"
CPU 被束缚在 100% 上,似乎 Nim 正在将数据复制到“生命”中,因为 RAM 使用率在“生成”后飙升。在 Nim 手册中,它谈到了并行块:
“生成的 proc 中使用的所有其他复杂位置位置 (spawn f(loc)) 必须在并行期间是不可变的 部分。这称为不可变性检查。目前不是 指定了“复杂位置”的确切含义。我们需要做到这一点 优化!
而且我非常使用它作为可变状态,所以也许这就是 Nim 复制数据的原因?如何绕过仅传递指针?几点:
- 我想我可以避免变异,而是返回被修改的新实例,但我仍然需要传入池和轮子才能从中读取。
- 如果无法使用 parallel: 语句,我将如何使用线程实现它?
- random() 线程安全吗?不然呢?
- 还有什么我可以做的不同吗?例如,更容易解开 FlowVar?
来自 Kotlin 的 Java8 Streams,我感到非常被宠坏了。
答: 暂无答案
评论