logo

Juliaでコードの性能を評価、ベンチマークする方法 📂ジュリア

Juliaでコードの性能を評価、ベンチマークする方法

概要

Juliaを使用する最大の理由が速度とパフォーマンスであるため、工学的に最適化されたコードを書くことは非常に重要である。BenchmarkTools.jlは、使いやすく便利でありながらも正確なパフォーマンス評価のインターフェースを提供する1

コード

julia> sinpi(0.5), cospi(0.5)
(1.0, 0.0)

julia> sincospi(0.5)
(1.0, 0.0)

例として、sincospiで一度に数値を計算する方法と、sinpicospiを別々に使用して計算する方法のパフォーマンスを比較してみよう。

@btime

評価結果から、sincospisinpiを一つだけ計算する状況では遅いが、cospiも別途計算するよりは速いことがわかる。このような評価結果は@timeと異なり、一度の実行ではなく自身で繰り返し測定したものであるため、より正確で信頼性がある。

julia> x = rand()
0.49058418112141866

julia> @btime SC = sincospi($x);
  7.500 ns (0 allocations: 0 bytes)

julia> @btime S = sinpi($x);
  4.500 ns (0 allocations: 0 bytes)

julia> @btime SC = sinpi($x), cospi($x);
  8.300 ns (0 allocations: 0 bytes)

ここで変数xの前に$を置く理由は、ベンチマークでxがグローバル変数として参照され、パフォーマンスそのものではなくオーバーヘッドを測定するのを防ぐためである。これにより、xはベンチマークの前に事前に計算され、ベンチマークに使用される。

@benchmark

より詳細なパフォーマンス評価結果を見るためには、@benchmarkマクロを使用する。次のようにヒストグラムを含め、視覚的にも優れた結果分析を出力する。

@time, @elapsedとの違い

@btimeは正確にパフォーマンスを評価する意図を持っているが、@timeは単に時間を測定するだけであり、@elapsedはその時間をFloat64で返すという違いがある。

パフォーマンスが優れたコードを書くために、@timeでコードの実行時間を測る習慣自体は非常に望ましいが2、根本的に@timeはコンパイル時間からあらゆるオーバーヘッドを含んでおり、正直にかかった時間は正確に把握できるものの、コード自体のパフォーマンスを評価するものとは言えない。

全コード

sinpi(0.5), cospi(0.5)
sincospi(0.5)

using BenchmarkTools
x = rand()
@btime SC = sincospi($x);
@btime S = sinpi($x);
@btime SC = sinpi($x), cospi($x);
@benchmark SC = sincospi($x)
@benchmark SC = sinpi($x), cospi($x)

環境

  • OS: Windows
  • julia: v1.10.0