Parcourir la source

Transférer les fichiers vers ''

Matthieu PUIGT il y a 5 ans
Parent
commit
09539351ba
5 fichiers modifiés avec 459 ajouts et 0 suppressions
  1. 64 0
      README.txt
  2. 288 0
      cfica.m
  3. 63 0
      demo1.m
  4. 44 0
      demo2.m
  5. BIN
      speech1.wav

Fichier diff supprimé car celui-ci est trop grand
+ 64 - 0
README.txt


+ 288 - 0
cfica.m

@@ -0,0 +1,288 @@
+% 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@lisic.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 & iter<iter_max
+    
+    y=w*x_prime;
+    
+    switch criterion
+        case 'k'
+        % kurtosis fixed-point iteration
+        w1=1/n*(y.^3)*x_prime'-3*w;
+        case 'g'
+        % Gaussian negentropic fixed-point iteration
+        gauss_y=exp(-y.^2/2);
+        w1=1/n*(y.*gauss_y)*x_prime' - 1/n*sum(((1-y.^2).*gauss_y))*w;
+        case 't'
+        % hyperbolic-tangent negentropic fixed-point iteration
+        tanh_y=tanh(y);
+        w1=1/n*tanh_y*x_prime' - 1/n*sum(1-tanh_y.^2)*w;
+    end
+    
+    % vector normalization
+    w1=w1./norm(w1);
+    
+    % computation of the stopping criterion
+    test=min([abs(w1-w) abs(w1+w)]);
+    w=w1;
+    
+    iter=iter+1;
+end
+
+%-------------------------------------------------------
+function [sc,c]=color(y,x,w1,w2,R1,R2)
+
+n=w2-w1+1;
+
+% computation of the autocorrelation matrix of y
+y2=y(w1+R1:w2+R1);
+for r=-R1:R2     
+    y1=y(w1-r:w2-r);      
+    Ry1(r+R1+1)=1/n*y1*y2';        
+end
+
+for r1=-R1:R2
+    for r2=-R1:R2
+        Ry(r1+R1+1,r2+R1+1)=Ry1(abs(r2-r1)+1);
+    end
+    % computation of the intercorrelation vector of y and x
+    y1=y(w1-r1:w2-r1);
+    ryx(r1+R1+1)=1/n*y1*(x(w1:w2))';
+end
+
+% computation of the wiener filter
+c=Ry^(-1)*ryx';
+
+% non-causal filtering process
+sc=filter_nc(c,y,R1);
+
+%-------------------------------------------------
+function x=conv_mix_nc(A,s,R1);
+% R1 non-causal coefficients
+% R2 strictly causal coefficients
+
+R2=size(A,3)-R1-1;
+
+for i=1:size(A,1)
+    x(i,:)=zeros(1,size(s,2)+R1+R2);
+    for j=1:size(s,1)
+        x(i,:)=x(i,:)+conv(reshape(A(i,j,:),size(A,3),1,1),s(j,:));
+    end
+end
+
+% removing of the out samples
+x=x(:,1+R1:end-R2);
+
+%-------------------------------------------------
+function s=filter_nc(h,e,R1);
+
+R2=length(h)-R1-1;
+
+% convolution process
+s=conv(h,e);
+
+% removing of the out samples
+s=s(1+R1:end-R2);
+
+%---------------------------------------------------
+function w1=reshape1(w,dims,order)
+
+% ordering of the tensor dimensions
+dims1=dims(order);
+
+% reshaping of the vector w
+w1=reshape(w,dims1);
+
+% re-ordering of the tensor
+w1=ipermute(w1,order);
+
+%-----------------------------------------------------
+function [criterion,initializ,epsi,Re,we1,we2,Rc,wc1,wc2,iter_max,verbose]=args(varargin,n)
+
+% ordering of the input arguments
+
+for i=1:length(varargin)
+    if length(varargin{i})==1
+    switch varargin{i}
+        case {'k','g','t'},criterion=varargin{i};
+        case 'i',initializ=1;
+        case 'v',verbose=1;
+        otherwise
+            if varargin{i}<1 & varargin{i}>0,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

+ 63 - 0
demo1.m

@@ -0,0 +1,63 @@
+% Demonstration program of the C-FICA algorithm used with artificial
+% colored sources and real filters
+
+clear all; clc; close all;
+
+% Number of samples
+T=5e4;
+
+% Choose the sources type
+% 1: MA with uniforms innovation processes
+% 2: MA with Laplacian innovation processes
+% 3: AR with uniforms innovation processes
+% 4: AR with Laplacian innovation processes
+choice=2;
+
+switch choice
+    case 1
+    s(1,:)=filter(rand(1,10),1,rand(1,T)-.5);
+    s(2,:)=filter(rand(1,10),1,rand(1,T)-.5);
+    case 2
+    s(1,:)=filter(rand(1,10),1,laplace(1,T));
+    s(2,:)=filter(rand(1,10),1,laplace(1,T));
+    case 3
+    s(1,:)=filter(1,[1 -.9],rand(1,T)-.5);
+    s(2,:)=filter(1,[1 -.9],rand(1,T)-.5);
+    case 4
+    s(1,:)=filter(1,[1 -.9],laplace(1,T));
+    s(2,:)=filter(1,[1 -.9],laplace(1,T));
+end
+
+% Definition of the filters by using the following data base:
+% B. Gardner and K. Martin. Head Related Transfer Functions of a Dummy Head
+% http://sound.media.mit.edu/ica-bench/.
+A(:,1,:)=hrtf(30);
+A(:,2,:)=hrtf(-80);
+
+% Convolutive mixing process
+x=conv_mix(A,s);
+
+% C-FICA algorithm
+[Sc,sc,Isc]=cfica(x,1e-16,80,400,'v');
+
+% Computation of the true contributions
+xc=contributions(A,s);
+
+% Identification of the source permutations
+perm=permutations(xc,sc);
+sc=sc(:,perm,:);Isc=Isc(:,perm);
+
+% SIRs computation
+SIR1=sir(xc(Isc(1),1,:),sc(Isc(1),1,:))
+SIR2=sir(xc(Isc(2),2,:),sc(Isc(2),2,:))
+
+% Plotting of the true (blue) and estimated (red) contributions
+figure
+hold on
+plot(squeeze(xc(Isc(1),1,:)));
+plot(squeeze(sc(Isc(1),1,:)),'r');
+
+figure
+hold on
+plot(squeeze(xc(Isc(2),2,:)));
+plot(squeeze(sc(Isc(2),2,:)),'r');

+ 44 - 0
demo2.m

@@ -0,0 +1,44 @@
+% Demonstration program of the C-FICA algorithm used with real speech
+% signals and real filters
+
+clear all; clc; close all;
+
+% Sources definition fs=20e3
+s(1,:)=wavread('speech1');
+s(2,:)=wavread('speech2');
+
+% Definition of the filter tensor by using the following data base:
+% B. Gardner and K. Martin. Head Related Transfer Functions of a Dummy Head
+% http://sound.media.mit.edu/ica-bench/.
+A(:,1,:)=hrtf(-10);
+A(:,2,:)=hrtf(40);
+
+% Convolutive mixing process
+x=conv_mix(A,s);
+
+% C-FICA algorithm (we choose [63000 63500] as an extraction window; we are 
+% currently working on an automatic choice of this window)
+[Sc,sc,Isc]=cfica(x,1e-16,[63000 63500],80,400,'v');
+
+% Computation of the true contributions
+xc=contributions(A,s);
+
+% Identification of the source permutations
+perm=permutations(xc,sc);
+sc=sc(:,perm,:);Isc=Isc(:,perm);
+
+% SIRs computation
+SIR1=sir(xc(Isc(1),1,:),sc(Isc(1),1,:))
+SIR2=sir(xc(Isc(2),2,:),sc(Isc(2),2,:))
+
+% Plotting of the true (blue) and estimated (red) contributions
+figure
+hold on
+plot(squeeze(xc(Isc(1),1,:)));
+plot(squeeze(sc(Isc(1),1,:)),'r');
+
+figure
+hold on
+plot(squeeze(xc(Isc(2),2,:)));
+plot(squeeze(sc(Isc(2),2,:)),'r');
+

BIN
speech1.wav