[英]power spectral density from fft result c#
我有一個Complex[]
(來自CsCore),這是我的FFT的結果。
Complex
具有float real
和float imaginary
。
由此我計算了以下內容
(double)index * sampleRate / FftSize;
Math.Sqrt(Math.Pow(real, 2) + Math.Pow(imaginary, 2));
Math.Atan(imaginary / real);
如果這些都是錯的,請糾正我。
根據我的理解,這是頻域信息,它允許我查看我的樣本中最常見的頻率。 現在我希望看到功率密度隨着時間的推移。 Matlab文檔顯示了示例,但我不明白,因為我不了解Matlab。 有人可以解釋有關此主題的Matlab文檔或幫助我實現C#實現嗎?
編輯:
這個答案建議簡單地調整幅度。 那是對的嗎?
實際上,正如我在其他答案中所述,您可以通過平方FFT結果的幅度來獲得功率譜密度(PSD)估計。 這基本上是您引用的Matlab文檔中的以下行(最多為縮放因子,對於大多數僅需要比較不同頻率組件的相對強度的應用程序而言,這並不重要):
psdx = (1/(Fs*N)) * abs(xdft).^2;
正如我在其他答案中所提到的,並且也在Matlab文檔中進行了描述,您可以通過在采用FFT之前將信號乘以窗口函數來獲得更好的PSD估計,並對多個FFT結果的平方幅度求平均值。
注意:對於階段,您可以更好地使用Math.Atan2(imaginary, real)
(參見MSDN上的Math.Atan2
),它涵蓋了輸入[-pi,pi]
范圍(而不是僅涵蓋[-pi/2,pi/2]
Math.Atan()
[-pi/2,pi/2]
)。
首先是Math.Sqrt(Math.Pow(real, 2) + Math.Pow(imaginary, 2));
已經實現為Complex.Magnitude
屬性 。 或者您可以使用Complex.Abs
方法 。
除了SleuthEye所說的,我還對功能實現進行了一些測量。
因為我不相信我實現的Math.Pow(x,2)
函數:
private static double Square(double value)
{
return value * value;
}
然而,事實證明C#已經優化了Math.Pow(x,2)
,所以它足夠快。 但無論如何:接下來我比較了三個實現
Square(testData[idx].Real) + Square(testData[idx].Imaginary);
Square(testData[idx].Magnitude);
Square(Complex.Abs(testData[idx]));
我的(平均)結果是(對於10,000,000個復雜元素):
所以似乎Magnitude屬性和Abs方法在內部使用平方根,這需要很多周期來處理。 但對於PSD你不需要那樣做。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.