52011


０~1を例えば１０万の目盛りでわけたいときに、以下のコードだとものすごく重くなってしまいます。

[code]

    function fs()
        Fs = Float64[]
        for i in 1:time
            push!(Fs,i/time)
        end
    end
    
[/code]

もっと軽快に動く書き方はありますでしょうか


CC BY-SA 4.0
2019-01-16T01:48:05.213
51999
2019-01-16T07:22:30.487
29111
question
julia
周波数を1次元配列にして出力する際、計算が異常に重くなる


自前でループを書くと遅くなりがちなので、ブロードキャストなどを利用するのが良いです。

[code]

    len=100000
    Fs = collect(1:len)
    Fs /= len
    
[/code]

あるいは、誤差が出る可能性に目をつむれば、

[code]

    Fs = collect(1/len:1/len:1)
    
[/code]

は、もうほんの少し速いと思います。


CC BY-SA 4.0
2019-01-16T05:47:54.320
52008
2019-01-16T05:47:54.320
3605
51999
answer


質問の趣旨からは離れますが、julia では BenchmarkTools パッケージを利用してベンチマークテストを実施することができます。

まず、fs 関数を以下の様に定義しておきます。

[code]

    function fs(time)
      Fs = Float64[]
      for i in 1:time
        push!(Fs, i/time)
      end
      return Fs
    end
    
[/code]

この fs 関数と `range() + collect()` での処理のベンチマークテストを行ってみます。

[code]

    julia> using BenchmarkTools
    julia> x = @benchmark fs(10^5)
    BenchmarkTools.Trial: 
      memory estimate:  2.00 MiB
      allocs estimate:  17
      --------------
      minimum time:     600.405 μs (0.00% GC)
      median time:      604.940 μs (0.00% GC)
      mean time:        613.886 μs (0.00% GC)
      maximum time:     1.098 ms (0.00% GC)
      --------------
      samples:          7819
      evals/sample:     1
    
    julia> y = @benchmark collect(range(0.0, stop=1.0, length=10^5))
    BenchmarkTools.Trial: 
      memory estimate:  781.33 KiB
      allocs estimate:  2
      --------------
      minimum time:     276.665 μs (0.00% GC)
      median time:      277.874 μs (0.00% GC)
      mean time:        291.672 μs (4.08% GC)
      maximum time:     40.080 ms (99.30% GC)
      --------------
      samples:          10000
      evals/sample:     1
    
[/code]

平均(mean)実行時間を比較してみます。

[code]

    julia> using Statistics
    julia> ratio(mean(y), mean(x))
    BenchmarkTools.TrialRatio: 
      time:             0.47512421388811227
      gctime:           Inf
      memory:           0.3813536701620591
      allocs:           0.11764705882352941
    
[/code]

実行時間は半分程度になりますが、`collect(range(...))` では GC(Garbage Collection)が発生していて、その場合は
40ms も掛かってしまっていることが判ります(実行環境や実行時の状況によりけりでしょうけれども)。

その他の手法があればベンチマークを実行して比較してみてはどうでしょうか。


CC BY-SA 4.0
2019-01-16T07:22:30.487
52011
2019-01-16T07:22:30.487
51999
answer