2017-07-07 32 views
3

私はすでにラプラスの方程式を解くためのシリアルコードを書いていますが、Juliaで並列に書こうとすると、シリアルのものよりも多くの時間とメモリが必要になります。私はそれの簡単な例を書いた。このコードをどのように並列化できますか?julia言語で単純なforループをどのように並列化するのですか?

ドメインt1があります。

t2

が計算され、その後 t1 = t2

@everywhere function left!(t1,t2,n,l_type,b_left,dx=1.0,k=50.0) 
    if l_type==1 
      for i=1:n 
       t2[i,1]=(b_left*dx/k)+t1[i,2]; 
       t1[i,1]=t2[i,1]; 
      end 
    else 
     for i=1:n 
     t1[i,1]=b_left; 
     end 
    end 
    return t1 end 

# parallel left does not work. 
@everywhere function pleft!(t1,t2,n,l_type,b_left,dx=1.0,k=50.0) 
    if l_type==1 
      @parallel for i=1:n 
       t2[i,1]=(b_left*dx/k)+t1[i,2]; 
       t1[i,1]=t2[i,1]; 
      end 
    else 
    @parallel for i=1:n 
     t1[i,1]=b_left; 
     end 
    end 
    return t1 
end 
n = 10; 
t1 = SharedArray(Float64,(n,n)); 
t2=t1; 
typ = 0; 
value = 10; 
dx = 1; 
k=50; 

@time t3 = pleft!(t1,t2,n,typ,value,dx,k) 
@time t2 = left!(t1,t2,n,typ,value,dx,k) 

答えは次のとおりです。

0.000872 seconds (665 allocations: 21.328 KB) # for parallel one 
0.000004 seconds (4 allocations: 160 bytes) #for usual one 

は、どのように私はこの問題を解決することができますか?

私はwhileループで以下を計算する必要があると計算した後。 私はコードの下に平行にする必要があります。

@everywhere function oneStepseri(t1,N) 
    t2 = t1; 
    for j = 2:(N-1) 
     for i = 2:(N-1) 
     t2[i,j]=0.25*(t1[i-1,j]+t1[i+1,j]+t1[i,j-1]+t1[i,j+1]); 
     end 
       end 
    return t2; 
end 

おかげで...

+0

タイミングの前にウォームアップを試みましたか?たとえば '@time rand(1000)'のようなタイミングを取るのではなく、まず 'rand(1000)'を3回または4回実行してJITがそれをコンパイルし、 '@ time'する必要があります。 – RedPointyJackson

+0

はい私はしました。 @timeそのもの。まだ遅すぎる。 –

答えて

0

私は多くのことを試してみました。 @parallelSharedArray,Distributed Arrayとし、ドメイン分割し、@spawnを使用する。スピードアップはなかった。 しかし、最近ジュリアは "Threads"を追加しました。あなたは、エクスポートによってスレッドを追加することができます。JULIA_NUM_THREADS=4 コマンドウィンドウ。 [email protected]を使用すると、コードを並列化できます。 スレッドの数を確認してくださいThreads.nthreads() ここに私のコードは そしてそれは私に良いスピードアップを与えます。

#to add threads export JULIA_NUM_THREADS=4 

nth = Threads.nthreads(); #print number of threads 

println(nth); 

a = zeros(10); 

[email protected] for i = 1:10 
      a[i] = Threads.threadid() 
     end 

show(a) 

b = zeros(100000); 
c = zeros(100000); 
b[1] = b[end] = 1; 
c[1] = c[end] = 1; 

function noth(A) 
    B = A; 
    for i=2:(length(A)-1) 
     B[i] = (A[i-1] + A[i+1])*0.5; 
    end 
    return B 
end 

function th(A) 
    B = A; 
    [email protected] for i=2:(length(A)-1) 
     B[i] = (A[i-1] + A[i+1])*0.5; 
    end 
    return B 
end 


println("warmup noth , th") 
@time bb = noth(b) 
@time cc = th(c) 
println("end ") 
@time bb = noth(b) 
@time cc = th(c) 

@time bb = noth(b) 
@time cc = th(c) 

@time bb = noth(b) 
@time cc = th(c) 
@time bb = noth(b) 
@time cc = th(c) 
@time bb = noth(b) 
@time cc = th(c) 
@time bb = noth(b) 
@time cc = th(c) 
show(bb[10]) 
println("\nbb ------------------------------------------------------------------------------------------------------------------> cc") 
show(cc[10]) 

答えは5つのスレッドと100000個のノードに対して、この

5                                          
[1.0,1.0,2.0,2.0,3.0,3.0,4.0,4.0,5.0,5.0]warmup noth , th                            
    0.008661 seconds (2.53 k allocations: 113.180 KB)                             
    0.020738 seconds (7.94 k allocations: 336.981 KB)                             
end                                         
    0.000446 seconds (4 allocations: 160 bytes)                               
    0.000122 seconds (6 allocations: 224 bytes)                               
    0.000437 seconds (4 allocations: 160 bytes)                               
    0.000135 seconds (6 allocations: 224 bytes)                               
    0.000435 seconds (4 allocations: 160 bytes)                               
    0.000115 seconds (6 allocations: 224 bytes)                               
    0.000447 seconds (4 allocations: 160 bytes)                               
    0.000112 seconds (6 allocations: 224 bytes)                               
    0.000440 seconds (4 allocations: 160 bytes)                               
    0.000109 seconds (6 allocations: 224 bytes)                               
    0.000439 seconds (4 allocations: 160 bytes)                               
    0.000116 seconds (6 allocations: 224 bytes)                               
0.052478790283203125                                     
bb ------------------------------------------------------------------------------------------------------------------> cc            
[email protected]:~/threads$                               

のようなものです。

ウォームアップにはスピードアップがないことに注意してください。それ以降はスピードアップがあります。

0.000446 seconds (4 allocations: 160 bytes) # usual code run      
0.000122 seconds (6 allocations: 224 bytes) #parallel code run       
+0

あなたがそれをより良くするものがあれば、私に知らせてください。それは高く評価されます。ありがとう。 –

関連する問題