나는 순간 주파수를 계산하는 원칙에 익숙하지 않아 많은 질문을 제기했습니다. 이 텍스트의 끝에있는 글 머리 기호 목록에서 모두 찾을 수 있습니다. 텍스트가 조금 길 수 있습니다. 실례합니다. 그러나 실제로 그 문제를 직접 해결하려고했습니다.
따라서 실제 값 신호 의 순간 주파수 에 관심이 있습니다. 분석 신호 의 도움으로 계산이 수행됩니다. 여기서 는 의 힐베르트 변환입니다 .
분석 신호 에서 순간 주파수를 계산하기 위해 나는 종이를 따랐다.
1992 년부터 Arthur E. Barns 의 순시 주파수 및 순시 대역폭 계산 .이 백서에서는 순시 주파수를 계산하는 여러 가지 방법을 소개합니다. 나는 그가 제안하고 사용한 모든 공식을 한 순간에 적어 둡니다.
"학습"을 위해 MATLAB에서 매우 간단하고 복잡한 신호 두 개를 가지고 놀았으며 순간 주파수를 얻고 싶었습니다.
Fs = 1000; % sampling-rate = 1kHz
t = 0:1/Fs:10-1/Fs; % 10s 'Timevector'
chirp_signal = chirp(t,0,1,2); % 10s long chirp-signal, signal 1
added_sinusoid = chirp_signal + sin(2*pi*t*10); % chirp + sin(10Hz), signal 2
modulated_sinusoid = chirp_signal .* sin(2*pi*t*10); % chirp * sin(10Hz), signal 3
이 세 가지 신호의 시간 영역 플롯은 다음과 같습니다.
논문의 모든 방법을 적용한 후 얻은 모든 순간 주파수의 도표는 다음과 같습니다.
순수한 처프 신호의 순간 주파수 : 사인파가 추가 된 처프 신호의 순간 주파수 : 변조 된 처프 신호의 순간 주파수 : 3 개의 이미지 모두에서 플롯 3과 4의 y 축이 확대되므로 그 진폭이 신호가 매우 작습니다!
분석 신호에서 순간 주파수까지 얻을 수있는 첫 번째 가능성은 다음과 같습니다.
여기서 는 순간 단계입니다. 나는 이것이 MATLAB의 웹 페이지 에서 오늘날 가장 일반적으로 사용되는 방법이라고 생각합니다 . 코드는 다음과 같습니다.
function [instantaneous_frequency] = f2(analytic_signal,Fs)
factor = Fs/(2*pi);
instantaneous_frequency = factor * diff(unwrap(angle(analytic_signal)));
% Insert leading 0 in return-vector to maintain size
instantaneous_frequency = [0 instantaneous_frequency];
end
논문에서 Barns는 이제 분석 신호에서 순간 주파수를 계산하는 다른 4 가지 방법을 제안합니다. 그는 또한 위의 공식을 언급하지만 단계의 모호성으로 인해 그것이 비현실적이라는 의견입니다. 나는 그 unwrap()
방법을 알지 못했고 그 뒤에 수학을 더 정확하게해야한다고 생각합니다. (저는 순간 주파수에 대한 다른 소스 코드를 볼 때 오늘 바로 그 방법에 대해 배웠습니다)
그의 논문에서이 수식에는 레이블 번호 (2)가 있으므로 f (t)에 색인 2를 부여했습니다. 다른 모든 색인은 논문의 번호와 동일한 방식으로 일치합니다.
그는 모호한 점 때문에 다음과 같이 제안합니다.
function [instantaneous_frequency] = f3(analytic_signal,Fs,T)
x = real(analytic_signal);
y = imag(analytic_signal);
diff_x = diff(x);
diff_y = diff(y);
factor = Fs/(2*pi);
a = x(2:end).*diff_y;
b = y(2:end).*diff_x;
c = x(2:end).^2;
d = y(2:end).^2;
instantaneous_frequency = factor * ((a-b)./(c+d));
% Insert leading 0 in return-vector to maintain size
instantaneous_frequency = [0 instantaneous_frequency];
end
그런 다음 Barner는 "즉시 주파수 근사치"라는 이름의 공식을 세 가지 더 제공합니다.
function[instantaneous_frequency] = f9(analytic_signal, Fs, T)
x = real(analytic_signal);
y = imag(analytic_signal);
factor = Fs/(2*pi*T);
a = x(1:end-T).*y(1+T:end);
b = x(1+T:end).*y(1:end-T);
c = x(1:end-T).*x(1+T:end);
d = y(1:end-T).*y(1+T:end);
instantaneous_frequency = factor.*atan((a-b)./(c+d));
% Append 0 to return-vector to maintain size
instantaneous_frequency = [instantaneous_frequency zeros(1,T)];
end
function [instantaneous_frequency] = f11(analytic_signal, Fs, T)
x = real(analytic_signal);
y = imag(analytic_signal);
factor = Fs/(4*pi*T);
a = x(1:end-2*T).*y(1+2*T:end);
b = x(1+2*T:end).*y(1:end-2*T);
c = x(1:end-2*T).*x(1+2*T:end);
d = y(1:end-2*T).*y(1+2*T:end);
instantaneous_frequency = factor.*atan((a-b)./(c+d));
% Append and insert 0s to maintain size
instantaneous_frequency = [zeros(1,T) instantaneous_frequency zeros(1,T)];
end
function [instantaneous_frequency] = formula14(analytic_signal, Fs, T);
x = real(analytic_signal);
y = imag(analytic_signal);
factor = 2*Fs/(pi*T);
a = x(1:end-T).*y(1+T:end);
b = x(1+T:end).*y(1:end-T);
c = (x(1:end-T)+x(1+T:end)).^2;
d = (y(1:end-T)+y(1+T:end)).^2;
instantaneous_frequency = factor * ((a-b)./(c+d));
% Append and insert 0s to maintain size
instantaneous_frequency = [instantaneous_frequency zeros(1,T)];
end
3 개의 근사 모두에서, 논문에서 제안 된 바와 같이, 공식 T는 Fs (T = Fs = 1000 = 1s)로 설정되었다.
이제 내 질문은 :
- 공식 f2 및 f3은 순수한 처프 신호에 대해 동일한 결과를 반환합니다. 나는 그들이 같은 것을 계산하기 때문에 그것이 좋다고 생각합니다. 세 가지 근사법은 같은 것을 반환하지 않으며 가까운 것도 아닙니다! 왜 그런가요? (나는 그것이 단지 프로그래밍 버그가 아니기를 바랍니다 ...)
- 비록 그들이 줄거리의 끝에서 같은 것을 반환하지만, 그들은 많이 흔들 리기 시작합니다 . 이에 대한 설명은 무엇입니까? 먼저 앨리어싱과 같은 것을 생각했지만 신호 주파수와 비교할 때 샘플링 주파수가 상당히 높으므로 제외 할 수 있다고 생각합니다.
최소한 f2 및 f3은 순수한 처프 신호에 대해 적절하게 작동하는 것처럼 보이지만 f2 및 f3을 포함한 모든 방법은 신호에서 둘 이상의 주파수에 대해 끔찍한 실패로 보입니다. 실제로 신호에 둘 이상의 주파수를 갖는 것이 항상 항상 그렇습니다. 그렇다면 어떻게 즉각적인 정확한 빈도를 얻을 수 있습니까?
- 신호에 둘 이상의 주파수가 존재할 때 실제로 무엇을 기대해야하는지조차 모릅니다. 계산은 주어진 시점에 대해 하나의 숫자를 반환하므로 여기에 더 많은 주파수가 존재할 때 어떻게해야합니까? 모든 주파수의 평균 또는 이와 유사한 것을 반환합니까?
그리고 아마도 가장 중요한 질문 은 실제로 정교하고 정교한 소프트웨어에서 어떻게 처리됩니까? 1.75 초에서 변조 된 신호의 순간 주파수를 알고 싶다고 가정하고 f2 방법을 선택했습니다. 운이 좋을 수도 있고 정답 일 가능성이 가장 높은 6 [Hz]에 가까운 숫자를 얻습니다. 불행히도 스파이크에서 값을 선택했기 때문에 결과를 옆에 몇 가지 샘플을 선택하고 갑자기 유선으로 연결하여 결과를 얻습니다. 어떻게 처리 할 수 있습니까? 평균 또는 더 나은 중간 필터로 후 처리합니까? 나는 심지어 많은 스파이크가 서로 인접한 지역에서 특히 어려울 수 있다고 생각합니다.
그리고 마지막으로 중요한 질문은 아닙니다. 왜 순간 주파수에서 찾은 대부분의 논문이 특히 지진과 같은 지진 학적 사건을 계산할 때 지리학 분야에서 나온 것입니까? Barne의 논문도이를 예로 들었습니다. 많은 영역에서 순간 주파수가 흥미롭지 않습니까?
그것은 지금까지 모든 답변에 대해 매우 감사합니다. 특히 누군가가 실제 소프트웨어 프로젝트 에서 구현하는 방법에 대한 팁을 줄 때 특히 그렇습니다 .)
친절한, 패트릭