% C-FICA algorithm - time-domain Convolutive extension of FastICA - v1.2 % % J. Thomas, Y. Deville and S. Hosseini % "Time-domain fast fixed-point algorithms for convolutive ICA", % IEEE Signal Processing Letters, vol. 13, no. 4, pp. 228-231, April 2006. % % % [Sc,sc,Isc,y,fe,fc,te,tc]=cfica(x,non-lin,epsi,Re,[we1 we2],Rc,[wc1 wc2],itermax,initializ,verbose) % % Inputs (place the deconvolution parameters before the recoloration ones % themselves before iter_max) % % x : observation vector % non-lin : 'k'->kurtosis, 'g'->Gaussian, 't'->tanh default 'g' % initializ : 'i' for initialization with unit filters optional % epsi : stopping criterion (between 0 and 1) default 10^-12 % Re : order of the extraction filters default 80 % [we1 we2] : extraction time window optional % Rc : order of the recoloration filters default 3R1 % [wc1 wc2] : recoloration time window optional % itermax : maximum number of iteration default 10000 % verbose : 'v' for verbose optional % % Outputs % % Sc : most powerful contributions for each estimated source % sc : estimated source contributions (tensor N*N*nb_samples) % Isc : indices of the most powerful contributions % y : N-1 estimated innovation processes (matrix (N-1)*nb_samples) % fe : extraction filters % fc : recoloration filters % te : times of extraction % tc : times of recoloration % ------------------------------------------------------------------------- % History of the software: % V1.1: original software written by J. Thomas % % V1.2: Error messages appeared with recent releases of Matlab in the function % conv_mix_nc. This version corrects them. % Author: Matthieu PUIGT Contact: matthieu.puigt@univ-littoral.fr % % ------------------------------------------------------------------------- function [Sc,sc,Isc,y,fe,fc,te,tc]=cfica(x,varargin) % N: number of observations, n: number of samples [N,n]=size(x); % centering of the observations x=x-mean(x,2)*ones(1,n); % ordering of the input arguments [criterion,initializ,epsi,Re,we1,we2,Rc,wc1,wc2,iter_max,verbose]=args(varargin,n); % R1 non-causal filter coefficients % R2 strictly causal filter coefficients R1=floor(Re/2);Rc1=floor(Rc/2); clear Re Rc R2=R1;Rc2=Rc1; % unit filter id=[zeros(1,R1),1,zeros(1,R2)]; % deflated observation vector x_def=x; for r=1:N-1 if verbose,fprintf('convolutive sphering %d .. \n',r),end tic % creation of a multi-delayed observation vector for k=1:N-r+1 for i=-R1:R2 x_tilde((R1+R2+1)*(k-1)+i+1+R1,:)=x_def(k,we1-i:we2-i); end end % whitening process [x_prime,B]=white(x_tilde,we2-we1+1); clear x_tilde; % initialization of the extraction process if initializ id1=id(ones(1,N-r+1),:); id1=reshape(id1',1,(N-r+1)*(R1+R2+1)); fe0=id1*B^-1; else fe0=ones(1,(N-r+1)*(R1+R2+1))*B^-1; end if verbose,fprintf('fixed-point extraction %d .. \n',r),end % extraction of a non-Gaussian innovation process [fe{r},iter]=extract(x_prime,fe0,criterion,epsi,iter_max); te(r)=toc; clear x_prime; fe{r}=fe{r}*B; % reshaping of the extraction vector fe{r}=reshape1(fe{r},[1,N-r+1,R1+R2+1],[3 2 1]); % application of the extraction filters y(r,:)=conv_mix_nc(fe{r},x_def(1:N-r+1,:),R1); for k=1:N % coloration of the r^th source for the r^th sensor if verbose,fprintf('recoloration process %d-%d .. \n',k,r),end tic [sc(k,r,:),fc{k,r}]=color(y(r,:),x(k,:),wc1,wc2,Rc1,Rc2); tc(k,r)=toc; end % removing of the last estimated contributions from the sensors for t=1:N s0(1,:)=sc(t,r,:); x_def(t,:)=x_def(t,:)-s0; end clear s0; end % the last contributions corresponding to the N^th source sc(:,N,:)=x_def; % identification of the most powerful contribution [M,Isc]=max(mean(sc.^2,3)); % output signals for k=1:N Sc(k,:)=sc(Isc(k),k,:); end %----------------------------------------- function [x_prime,B]=white(x_tilde,n) % eigendecomposition of xxt [E,D]=eig(x_tilde*x_tilde'); % computation of whitening matrix sqD=sqrt(n)*D^(-1/2); B=sqD*E'; % whitening process x_prime=B*x_tilde; %------------------------------------------------------------ function [w,iter]=extract(x_prime,w,criterion,epsi,iter_max) [N,n]=size(x_prime); % extraction vector normalization w=w./norm(w); test=1;iter=0; while test>epsi & iter0,epsi=varargin{i}; else,if ~exist('Re'),Re=varargin{i}; else,if ~exist('Rc'),Rc=varargin{i}; else iter_max=varargin{i};end,end,end end else,if ~exist('we1'),we1=varargin{i}(1);we2=varargin{i}(2); else,wc1=varargin{i}(1);wc2=varargin{i}(2);end end end if ~exist('criterion'), criterion='g';end if ~exist('initializ'), initializ=0;end if ~exist('epsi'), epsi=1e-12;end if ~exist('Re'), Re=80;end if ~exist('we1'), we1=Re+1;we2=n-Re-1;end if ~exist('Rc'), Rc=2*Re;end if ~exist('wc1'), wc1=Rc+1;wc2=n-Rc-1;end if ~exist('iter_max'), iter_max=1e4;end if ~exist('verbose'), verbose=0; end if verbose,criterion,initializ,epsi,Re,extr_window=[we1,we2],Rc,col_window=[wc1,wc2],iter_max,verbose,end