私が最新の編集で書いた方法は、サンプルサイズが非常に大きくなるまで、よりも高速scipy.statstools.acf
になりました。fft=True
エラー分析バイアスを調整し、非常に正確なエラー推定値を取得したい場合: Ulli Wolff によるこの論文を実装する私のコードをここで見てください(または UW によるオリジナル)Matlab
テストされた機能
a = correlatedData(n=10000)
ここにあるルーチンからのものです
gamma()
と同じ場所からですcorrelated_data()
acorr()
以下の私の機能です
estimated_autocorrelation
別の回答で見つかりました
acf()
からfrom statsmodels.tsa.stattools import acf
タイミング
%timeit a0, junk, junk = gamma(a, f=0) # puwr.py
%timeit a1 = [acorr(a, m, i) for i in range(l)] # my own
%timeit a2 = acf(a) # statstools
%timeit a3 = estimated_autocorrelation(a) # numpy
%timeit a4 = acf(a, fft=True) # stats FFT
## -- End pasted text --
100 loops, best of 3: 7.18 ms per loop
100 loops, best of 3: 2.15 ms per loop
10 loops, best of 3: 88.3 ms per loop
10 loops, best of 3: 87.6 ms per loop
100 loops, best of 3: 3.33 ms per loop
編集...サンプルを保持l=40
して変更n=10000
することを再度確認しn=200000
、FFTメソッドが少し牽引力を獲得し始め、statsmodels
fftの実装がそれを縁取りました...(順序は同じです)
## -- End pasted text --
10 loops, best of 3: 86.2 ms per loop
10 loops, best of 3: 69.5 ms per loop
1 loops, best of 3: 16.2 s per loop
1 loops, best of 3: 16.3 s per loop
10 loops, best of 3: 52.3 ms per loop
編集 2: ルーチンを変更し、FFT との比較を再テストしましn=10000
たn=20000
a = correlatedData(n=200000); b=correlatedData(n=10000)
m = a.mean(); rng = np.arange(40); mb = b.mean()
%timeit a1 = map(lambda t:acorr(a, m, t), rng)
%timeit a1 = map(lambda t:acorr.acorr(b, mb, t), rng)
%timeit a4 = acf(a, fft=True)
%timeit a4 = acf(b, fft=True)
10 loops, best of 3: 73.3 ms per loop # acorr below
100 loops, best of 3: 2.37 ms per loop # acorr below
10 loops, best of 3: 79.2 ms per loop # statstools with FFT
100 loops, best of 3: 2.69 ms per loop # statstools with FFT
実装
def acorr(op_samples, mean, separation, norm = 1):
"""autocorrelation of a measured operator with optional normalisation
the autocorrelation is measured over the 0th axis
Required Inputs
op_samples :: np.ndarray :: the operator samples
mean :: float :: the mean of the operator
separation :: int :: the separation between HMC steps
norm :: float :: the autocorrelation with separation=0
"""
return ((op_samples[:op_samples.size-separation] - mean)*(op_samples[separation:]- mean)).ravel().mean() / norm
4x
高速化は以下で達成できます。そうしないとop_samples=a.copy()
配列が変更されるため、渡すだけに注意する必要があります。a
a-=mean
op_samples -= mean
return (op_samples[:op_samples.size-separation]*op_samples[separation:]).ravel().mean() / norm
サニティーチェック

エラー分析の例
これは少し範囲外ですが、統合された自己相関時間または統合ウィンドウの計算なしで図をやり直すことはできません。エラーを伴う自己相関は、下のプロットで明確です
