A
download zcross.m
Language: Matlab
License: GPL
Copyright: Copyright 1998,2000 Julian Andrew de Marchi, Ph.D. (julian@matlinks.net)
LOC: 42
Project Info
MatLinks/Chorus(matlinks)
Server: SourceForge
Type: cvs
...opyleft\gpl\chorale\signal\
   average.m
   beatfreq.m
   Contents.m
   envelope.m
   findpeak.m
   morlet.m
   phdiff.m
   smooth.m
   zcross.m

% ZCROSS  ( MatLinks) Find the zero crossings of an arbitrary function.
%
%    ZCROSS(X) finds the zero crossings in the given data vector X.
%
%    ZCROSS(X,W) ignores multiple (noisy) zero crossings occurring within
%    a moving window of length W.  The default value for W=1.
%
%    ZCROSS(...,'exact') linearly interpolates the data to yield the "exact"
%    zero crossings.  In this case the result will contain non-integer "indices"
%    into the data X which correspond to the interpolated zero crossing points.
%    Applying ROUND(ZCROSS(*)) will subsequently yield the integer-valued
%    indices of X closest to the actual zero crossings.
%
%    ZCROSS(...) plots X and marks the zero crossings.  I = ZCROSS(...) returns
%    the indices I closest to each zero crossing.  LENGTH(I) will thus equal the
%    total number of zero crossings.
%
%    [I,D]=ZCROSS(...) also returns the mean deviation from true zero at the
%    "zero" crossings.  If [I,D]=ZCROSS(...) is used with the 'exact' parameter,
%    D will yield the mean deviation from the interpolated zero crossing points.
%
%    When no zero crossings are found, I=0 is returned.
%
%    See also FINDPEAK.
%
%    Type HELP MATLINKS for a full listing of all MatLinks ToolChest functions.
%
function [I, D] = zcross(data, w, exact)
%===============================================================================
%  Copyright  1998,2000 Julian Andrew de Marchi, Ph.D. (julian@matlinks.net)
%  Use & distribution covered by GNU General Public License (www.gnu.org)
%===============================================================================

%------------------
% parse the inputs
%------------------
if (nargin==0), error('No data vector X supplied.');
elseif (nargin<2), w=1; exact=0;
elseif (nargin==2), exact=num2str(w);
  if (exact(1)>='0' & exact(1)<='9'), w=str2num(exact); exact=0;
  else w=1; exact=1; end;
elseif (exact~='exact')
  error('"exact" is the only valid interpolation.');
else exact=1;
end;
if (w~=fix(w) | w<=0),
  error('The window length W must be a positive integer.');
elseif (length(data)<w+1)
  error('Not enough data in X--zero crossing detection would be senseless.');
end;

%---------------------------
% locate the zero crossings
%---------------------------
ii=0;  II=1;  I(1) = 0;
for ix=2:length(data),
  if (sign(data(ix))~=sign(data(ix-1)) & sign(data(ix))~=0),
    if (ix-II>=w | II<w), ii=ii+1;
      if (exact), I(ii)=data(ix-1)/(data(ix-1)-data(ix))+ix-1;
      else II=ix-1; [dummy inx]=min(abs(data(II:ix))); I(ii)=II+inx-1; end;
    end;
  end;
end;
if (exact), D=zeros(1,ii);
  for ix=2:ii,
    II=abs((data(round(I(ix)))-data(round(I(ix-1))))*(I(ix)-floor(I(ix)))+data(round(I(ix-1))))/(ii-1);
    D(ix-1)=D(ix-1)+II; D(ix)=D(ix)+II;
  end;
  D(1)=2*D(1); D(ii)=2*D(ii); D=D./2;
else
  P = mean(abs(data(I)));
end;

%-------------------------------------------------------
% plot the zero crossings if there's no output variable
%-------------------------------------------------------
if (nargout==0),
  hold off, plot(data), hold on, plot(1:length(data), data, 'c.');
  if (exact), plot(I, D(1:ii), 'mo'), title(['Interpolated zero crossings (w=' num2str(w) ')']);
  else plot(I, data(I), 'mo'), title(['Zero crossings (w=' num2str(w) ')']); end;
  if (exact),
    plot(1:length(data), ones(1,length(data))' * [max(D) min(D)], 'c:'), xlabel('i'), ylabel('x(i)');
  end;
  zoom on;
end;

%===============================================================================
% End-of-File
%===============================================================================

About Koders | Resources | Downloads | Support | Black Duck | Terms of Service | DMCA | Privacy Policy | Contact Us