%================ Reconstruct parameters of the component ================= %============== from its time-frequency support in WFT or WT ============== % Version 1.01 stable %-------------------------------Copyright---------------------------------- % % Author: Dmytro Iatsenko % Information about these codes (e.g. links to the Video Instructions), % as well as other MatLab programs and many more can be found at % http://www.physics.lancs.ac.uk/research/nbmphysics/diats/tfr % % Related articles: % [1] D. Iatsenko, A. Stefanovska and P.V.E. McClintock, % "Linear and synchrosqueezed time-frequency representations revisited. % Part I: Overview, standards of use, related issues and algorithms." % {preprint:arXiv:1310.7215} % [2] D. Iatsenko, A. Stefanovska and P.V.E. McClintock, % "Linear and synchrosqueezed time-frequency representations revisited. % Part II: Resolution, reconstruction and concentration." % {preprint:arXiv:1310.7274} % %------------------------------Documentation------------------------------- % % [iamp,iphi,ifreq,Optional:rtfsupp] = rectfr(tfsupp,TFR,freq,wopt,Optional:method) % - returns the component's amplitude [iamp], phase [iphi] and frequency % [ifreq] as reconstructed from its extracted time-frequency support % [tfsupp] in the signal's WFT/WT [TFR] (determines whether TFR is WFT % or WT based on the spacings between specified frequencies [freq] - % linear (WFT) or logarithmic (WT)). The optional output [rtfsupp] % returns the extracted time-frequency support if the input [tfsupp] % specifies 1xL frequency profile instead of the full time-frequency % support (see below); otherwise returns input [rtfsupp]=[tfsupp]. % % INPUT: % tfsupp: 3xL matrix (or 1xL vector of the desired frequency profile) % - extracted time-frequency support of the component, containing % frequencies of the TFR amplitude peaks (ridge points) in the % first row, support lower bounds (referred as \omega_-(t)/2/pi % in [1]) - in the second row, and the upper bounds (referred as % \omega_+(t)/2/pi in [1]) - in the third row. Alternatively, one % can specify [tfsupp] as 1xL vector of the desired frequency % profile, in which case the program will automatically select % time-frequency support around it and the corresponding peaks. % TFR: NFxL matrix (rows correspond to frequencies, columns - to time) % - time-frequency representation (WFT or WT), to which [tfsupp] % correspond % freq: NFx1 vector % - the frequencies corresponding to the rows of [TFR] % wopt: structure returned by function wft.m or wt.m % - parameters of the window/wavelet and the simulation, returned as % a third output by functions wft, wt; [wopt] contains all the % needed information, i.e. name of the TFR, sampling frequency, % window/wavelet characteristics etc. % method:'direct'(default)|'ridge'|'both' % - the reconstruction method to use for estimating the component's % parameters [iamp], [iphi], [ifreq] (see [1]); if set to 'both', % all parameters are returned as 2xL matrices with direct and % ridge estimates corresponding to 1st and 2nd rows, respectively. % % NOTE: in the case of direct reconstruction, if the window/wavelet does % not allow direct estimation of frequency, i.e. [wopt.wp.omg=Inf] for % the WFT or [wopt.wp.D=Inf] for the WT (as for the Morlet wavelet), % corresponding to infinite \bar{\omega}_g or D_\psi (in the notation of % [1]), then the frequency is reconstructed by hybrid method (see [1]). % %-------------------------------Examples----------------------------------- % % /Calculate first WFT (see wft function):/ % [WFT,freq,wopt]=wft(sig,fs,...(parameters)); % /Extract somehow the component time-frequency support from it, e.g./ % tfsupp=ecurve(WFT,freq,wopt); % /Then component's parameters can be reconstructed from its extracted % WFT support [tfsupp] as/ % [iamp,iphi,ifreq]=rectfr(tfsupp,WFT,freq,wopt); % /For WT the same procedure is used./ % %------------------------------Changelog----------------------------------- % % v1.01: % - some minor changes plus better optimization % - added possibility to specify [tfsupp] as frequency profile % - added possibility to specify reconstruction method % - added some other possibilities % - for simplicity, only the direct estimates are now returned by default % %-------------------------------------------------------------------------- function [iamp,iphi,ifreq,varargout] = rectfr(tfsupp,TFR,freq,wopt,varargin) [NF,L]=size(TFR); freq=freq(:); fs=wopt.fs; wp=wopt.wp; method=1; if nargin>4 && ~isempty(varargin{1}) if strcmpi(varargin{1},'direct'), method=1; elseif strcmpi(varargin{1},'ridge'), method=2; else method=0; end end idt=1:L; if iscell(tfsupp), idt=tfsupp{2}; tfsupp=tfsupp{1}; end %Define component parameters and find time-limits NR=2; if method==1 || method==2, NR=1; end, NC=length(idt); mm=ones(NR,NC)*NaN; ifreq=mm; iamp=mm; iphi=mm; asig=mm; tn1=find(~isnan(tfsupp(1,:)),1,'first'); tn2=find(~isnan(tfsupp(1,:)),1,'last'); %Determine the frequency resolution and transform [tfsupp] to indices if freq(1)<=0 || std(diff(freq))NF)=NF; %Define variables to not use cells or structures C=wp.C; ompeak=wp.ompeak; fwtmax=wp.fwtmax; if isfield(wp,'omg'), omg=wp.omg; else D=wp.D; end if ~iscell(wp.fwt), fwt=wp.fwt; nflag=0; else nflag=1; Lf=length(wp.fwt{2}); if strcmpi(fres,'linear'), fxi=wp.fwt{2}; fwt=wp.fwt{1}; else fxi=linspace(min(wp.fwt{2}),max(wp.fwt{2}),Lf)'; fwt=interp1(wp.fwt{2},wp.fwt{1},fxi,'spline'); end wstep=mean(diff(fxi)); end %If only the frequency profile is specified, extract the full time-frequency support if min(size(tfsupp))==1 eind=tfsupp(:)'; tfsupp=zeros(3,L)*NaN; for tn=tn1:tn2 cind=eind(tn); xn=idt(tn); cs=abs(TFR(:,xn)); %Ridge point cpeak=cind; if cind>1 && cind=cs(cind-1:end-2) & cs(cind:end-1)>cs(cind+1:end),1,'first'); cpeak1=min([cpeak1,NF]); cpeak2=cind+1-find(cs(cind:-1:2)>=cs(cind+1:-1:3) & cs(cind:-1:2)>cs(cind-1:-1:1),1,'first'); cpeak2=max([cpeak2,1]); if cs(cpeak1)>0 && cs(cpeak2)>0 if cpeak1-cind==cind-cpeak2 if cs(cpeak1)>cs(cpeak2), cpeak=cpeak1; else cpeak=cpeak2; end elseif cpeak1-cindcind-cpeak2, cpeak=cpeak2; end elseif cs(cpeak1)==0, cpeak=cpeak2; elseif cs(cpeak2)==0, cpeak=cpeak1; end elseif cs(cind+1)>cs(cind-1) cpeak=cind-1+find(cs(cind:end-1)>=cs(cind-1:end-2) & cs(cind:end-1)>cs(cind+1:end),1,'first'); cpeak=min([cpeak,NF]); elseif cs(cind+1)cs(cind-1:-1:1) & cs(cind:-1:2)>=cs(cind+1:-1:3),1,'first'); cpeak=max([cpeak,1]); end elseif cind==1 if cs(2)=cs(cind:end-2) & cs(cind+1:end-1)>cs(cind+2:end),1,'first'); cpeak=min([cpeak,NF]); end elseif cind==NF if cs(NF-1)cs(cind-2:-1:1) & cs(cind-1:-1:2)>=cs(cind:-1:3),1,'first'); cpeak=max([cpeak,1]); end end tfsupp(1,tn)=cpeak; %Boundaries of time-frequency support iup=[]; idown=[]; if cpeak2, idown=cpeak-find(cs(cpeak-1:-1:2)<=cs(cpeak:-1:3) & cs(cpeak-1:-1:2)3, varargout{1}=tfsupp*NaN; varargout{1}(:,tn1:tn2)=freq(tfsupp(:,tn1:tn2)); end %==================================WFT===================================== if strcmpi(fres,'linear') %Direct reconstruction------------------------------------------------- if method==0 || method==1 for tn=tn1:tn2 ii=tfsupp(2,tn):tfsupp(3,tn); xn=idt(tn); cs=TFR(ii,xn); if ~isfinite(omg) if xn>idt(tn1) && xn1 && ipeak1 && ipeakidt(tn1) && xn1 && ipeak1 && ipeak