juliaの速度を試してみる(vs python)

pythonが遅くてイライラするあなたへ

pythonっていうかscript言語全般、for文おっせーよな!(湯川専務が聞いている風) ってか動的型付けなんて速度出るわけねーよな!

って思ってる方はたくさんいるかと思いますし、 それを克服したjulia言語が速いってことを知っている人も多いかと思いますが、 本当にそうなの?ってところでjuliaも1.0が出たことだし実験してみました。

Juliaデータサイエンス―Juliaを使って自分でゼロから作るデータサイエンス世界の探索

Juliaデータサイエンス―Juliaを使って自分でゼロから作るデータサイエンス世界の探索

等差級数を足して見よう、一億ループ。

1 + 2 + … + 99999999 + 100000000 = 5000000050000000 の計算を愚直に。forループで。vs python。ファイ!

さて、まずはpython。(ipythonのマジックコードの%timeで計測)

# python
a = 0
%time for x in range(1,100000001):a += x
print(a)

結果は…

Wall time: 8.36 s
5000000050000000

まぁこんなもん。知ってるよ。遅いの。

さて、pythonのfor文は遅いのは当たり前なので、 numpyでやってみましょう。

入門 Python 3

入門 Python 3

# numpy
import numpy as np
%time a = np.arange(100000001,dtype="uint64").sum()
print(a)

結果は…

Wall time: 341 ms
5000000050000000

うん。速い。裏側Cで動いているもの。

さて、julia。

とりあえず普通に書いて実行。 こちらもマジックコード@timeで計測。

# julia
a = 0
@time for x in 1:100000000
    global a
    a += x
end
println(a)

はてさて結果は…

4.214371 seconds (200.00 M allocations: 2.980 GiB, 0.82% gc time)

ぬぬぅ?1/2くらいにはなってるけどこんなもん?イマイチ?

この記事によると、 juliaは関数化しないとおっせーよ!ってことらしい。

さて、もう一度。

# julia func
a=0
function f()
    for x in 1:100000000
        global a
        a += x
    end
    println(a)
end
@time f()

はてさて…

5000000050000000
  2.281576 seconds (200.01 M allocations: 2.981 GiB, 1.61% gc time)

さらに1/2になったけど、そこまで…?

function内で結果を返すのではなく、returnさせてみるか。

# julia func2
a=0
function f(a)
    for x in 1:100000000
        a += x
    end
    return a
end

@time f(a)
print(a)

はてさて…

  0.004785 seconds (11.61 k allocations: 631.791 KiB)
5000000050000000

こ  れ  だ …  !

えらいこっちゃ。 5msですってよ、奥様。 pythonの8秒の1000倍以上の速度!

numpyより速E。 これはすごE。

最後にjuliaもnumpyのarange関数みたいにcollect関数があるのでそれをsumしてみる。

# julia collect
@time println(sum(collect(1:100000000)))

はてさて…

5000000050000000
  0.277942 seconds (15 allocations: 762.940 MiB, 5.22% gc time)

う、うん。まぁまぁ。悪くないよ。

結論

関数で値を返すと爆速。 pythonの1000倍以上出ることもある。

番外編

スクリプト言語最速と噂のjavascriptで。 google chromeのconsoleから実行。

a = 0;
const startTime = performance.now();
for (  var i = 1;  i <= 100000000;  i++  ) {
    a = a + i;
}
const endTime = performance.now();
console.log(endTime - startTime);
console.log(a)

はてさて。

2101.399999999441
5000000050000000

2秒ですか。まぁ悪くないですね。 node.jsから実行したらまたちょっと違うかもね。

Node.js超入門[第2版]

Node.js超入門[第2版]

ざっつおーるせんきゅー。