为什么共享阵列在操作后不正确?



我有以下简单的代码可以使用@distributed命令来理解,如文档 https://docs.julialang.org/en/v1/manual/parallel-computing/#Multi-Core-or-Distributed-Processing-1:

using Distributed
using SharedArrays
using DelimitedFiles
f(x) = x^2
t = collect(-1:0.001:1)
y = SharedArray{Float64}(size(t,1))
@distributed for i in 1:size(t,1)
y[i] = f(t[i])
end
file = open("foo.dat", "w")
writedlm(file, [t, y])
close(file)

但是当我打开文件data = readdlm("foo.dat")时,y值都是零。有趣的是,如果我运行一个 Jupyter 笔记本和文件写入部分,

file = open("foo.dat", "w")
writedlm(file, [t, y])
close(file)

位于不同的单元格中,则文件包含正确的内容。这在运行数据写入命令的 REPL 中是一致的。此外,如果上面的代码在脚本中,则foo.dat文件也不正确,除非我在处理ywritedlm命令之前有一些东西。例如,在writedlm(file, [t, y])之前有println(y),那么foo.dat将包含正确的内容。我有什么地方做得不对吗?似乎有一种解决方法,只需在将y写入文件之前对其进行处理即可,但这似乎是一个奇怪的错误,我想知道是否有人有任何建议,或者这是否应该作为问题提出在 GitHub 上

@distributed使用绿色线程异步启动分布式计算来控制它们。您应该等到它们完成后再进一步处理数据(例如写入文件(。

因此,您的循环应如下所示:

@sync @distributed for i in 1:size(t,1)
y[i] = f(t[i])
end

此外,您的代码不会生成任何工作进程。 您可以运行一个示例来添加两个工作线程:

addprocs(2)

但随后您会注意到@distributed循环崩溃,因为您的f函数应该在所有工作进程中定义,而不仅仅是主进程。因此,您的代码应如下所示:

@everywhere f(x) = x^2

上面的行应该在addprocs命令之后

快乐的分布式计算!

最新更新