Làm cách nào để tạo trục tần số cho chiều dài FFT chẵn và lẻ?


12

Tôi có thể được trợ giúp về cách làm cho trục tần số chuyển từ tần số âm sang tần số dương, (trong Hertz), đó sẽ là trục x trong kết quả FFT, nhưng được đưa ra FFT có độ dài chẵn hoặc FFT có độ dài lẻ. Tôi gặp một số rắc rối khi thực hiện nó trong MATLAB. (Giả sử bạn biết tần số lấy mẫu f_s).


1
Nó có thể giúp bạn suy nghĩ về các tần số được đặt cách đều nhau xung quanh vòng tròn đơn vị. Ví dụ, FFT 4 điểm có các tần số ở [0 / 4fs, 1 / 4fs, 2 / 4fs, 3 / 4fs], thường được viết là [0, fs / 4, fs / 2, -fs / 4]. FFT 3 điểm có các thùng tần số ở [0 / 3fs, 1 / 3fs, 2 / 3fs] hoặc có thể được viết là [0, fs / 3, -fs / 3]. Đối với kích thước lẻ, khoảng cách bằng nhau này bỏ qua tần số Nyquist, nhưng luôn bao gồm 0.
endolith

@endolith Sự tương tự này đã giúp tôi rất nhiều, cảm ơn bạn rất nhiều!
Đánh dấu LeMoine

Câu trả lời:


5

Một cách tiếp cận đơn giản là tính toán vectơ tần số cho đầu ra DFT chưa được dịch chuyển (tức là những gì bạn sẽ nhận được trực tiếp từ fft()hàm MATLAB , mà không thực hiện fftshift()), sau đó ánh xạ lại các tần số tương ứng với các vị trí ở phía âm của trục. Thí dụ:

% assume input signal "x", sampling frequency "fs"
% calculate FFT
X = fft(x,Nfft);
% calculate frequency spacing
df = fs / Nfft;
% calculate unshifted frequency vector
f = (0:(Nfft-1))*df;
% move all frequencies that are greater than fs/2 to the negative side of the axis
f(f >= fs/2) = f(f >= fs/2) - fs;
% now, X and f are aligned with one another; if you want frequencies in strictly
% increasing order, fftshift() them
X_normal_order = fftshift(X);
f_normal_order = fftshift(f);

Câu trả lời được cung cấp bởi learnvst cũng nên hoạt động; đây chỉ là một cách nghĩ khác về nó mà không yêu cầu bất kỳ vỏ đặc biệt nào cho kích thước DFT chẵn / lẻ.


Xin chào JasonR, có chắc chắn rằng mã này đang hoạt động không, vì nếu tôi thử nó với fs = 1000 và Nfft = 256, f_n normal_order tôi nhận được bắt đầu bằng một số dương, trở nên âm tính và sau đó tích cực trở lại. Ngoài ra độ dài không phù hợp.
TheGrapeBeyond

Xin lỗi, đã sửa một vài lỗi chính tả trong mã. Nó nên hoạt động ngay bây giờ.
Jason R

9

Bạn có thể tạo phổ tần số dương khá đơn giản (trong đó fstỷ lệ lấy mẫu và NFFTlà số thùng fft). Trong triển khai Matlab của thuật toán FFT, phần tử đầu tiên luôn là thành phần DC, do đó tại sao mảng bắt đầu từ 0. Điều này đúng với các giá trị lẻ và chẵn của NFFT.

%//Calculate frequency axis
df = fs/NFFT;
fAxis = 0:df:(fs-df);

Nếu bạn cần bọc phổ tần số, bạn cần tính đến việc bạn có một NFFT được đánh số lẻ hay không. Luôn luôn cần phải có một thành phần DC , vì vậy. .

df = fs/NFFT;
fAxis = (0:df:(fs-df)) - (fs-mod(NFFT,2)*df)/2;

Lưu ý cách tính toán trục tần số dương giống hệt như trên, nhưng thuật ngữ thay đổi FFT thay đổi thành độ dài FFT chẵn hoặc lẻ.

Các đoạn mã này được lấy từ một câu trả lời dài được đăng trên SO (mà bạn có thể thấy thú vị) được tìm thấy ở đây: /programming/9694297/matlab-fft-xaxis-limits-messing-up-and-fftshift/ 9699983 # 9699983


Được rồi, vậy tôi có thể sử dụng cái này cho NFFT lẻ không?
TheGrapeBeyond

Ồ xin lỗi. Tôi thấy các biến chứng nhẹ khi đi từ tần số -ve đến + ve. Tôi đã thay đổi câu trả lời một chút.
học
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.