]> Creatis software - CreaPhase.git/blobdiff - octave_packages/m/polynomial/conv.m
update packages
[CreaPhase.git] / octave_packages / m / polynomial / conv.m
diff --git a/octave_packages/m/polynomial/conv.m b/octave_packages/m/polynomial/conv.m
new file mode 100644 (file)
index 0000000..0d087e7
--- /dev/null
@@ -0,0 +1,141 @@
+## Copyright (C) 1994-2012 John W. Eaton
+##
+## This file is part of Octave.
+##
+## Octave is free software; you can redistribute it and/or modify it
+## under the terms of the GNU General Public License as published by
+## the Free Software Foundation; either version 3 of the License, or (at
+## your option) any later version.
+##
+## Octave is distributed in the hope that it will be useful, but
+## WITHOUT ANY WARRANTY; without even the implied warranty of
+## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+## General Public License for more details.
+##
+## You should have received a copy of the GNU General Public License
+## along with Octave; see the file COPYING.  If not, see
+## <http://www.gnu.org/licenses/>.
+
+## -*- texinfo -*-
+## @deftypefn  {Function File} {} conv (@var{a}, @var{b})
+## @deftypefnx {Function File} {} conv (@var{a}, @var{b}, @var{shape})
+## Convolve two vectors @var{a} and @var{b}.
+##
+## The output convolution is a vector with length equal to
+## @code{length (@var{a}) + length (@var{b}) - 1}.
+## When @var{a} and @var{b} are the coefficient vectors of two polynomials, the
+## convolution represents the coefficient vector of the product polynomial.
+##
+## The optional @var{shape} argument may be
+##
+## @table @asis
+## @item @var{shape} = "full"
+## Return the full convolution.  (default)
+##
+## @item @var{shape} = "same"
+## Return the central part of the convolution with the same size as @var{a}.
+## @end table
+##
+## @seealso{deconv, conv2, convn, fftconv}
+## @end deftypefn
+
+## Author: Tony Richardson <arichard@stark.cc.oh.us>
+## Created: June 1994
+## Adapted-By: jwe
+
+function y = conv (a, b, shape = "full")
+
+  if (nargin < 2 || nargin > 3)
+    print_usage ();
+  endif
+
+  if (! (isvector (a) && isvector (b)))
+    error ("conv: both arguments A and B must be vectors");
+  elseif (nargin == 3 && ! any (strcmpi (shape, {"full", "same"})))
+    error ('conv: SHAPE argument must be "full" or "same"');
+  endif
+
+  la = length (a);
+  lb = length (b);
+
+  ly = la + lb - 1;
+
+  if (ly == 0)
+    y = zeros (1, 0);
+    return;
+  endif
+
+  ## Use shortest vector as the coefficent vector to filter.
+  if (la > lb)
+    [a, b] = deal (b, a);  # Swap vectors 
+    lb = la;
+  endif
+  x = b;
+
+  ## Pad longer vector to convolution length.
+  if (ly > lb)
+    x(end+1:end+ly-lb) = 0;
+  endif
+
+  y = filter (a, 1, x);
+
+  if (strcmp (shape, "same"))
+    idx = ceil ((ly - la) / 2);
+    y = y(idx+1:idx+la);
+  endif
+
+endfunction
+
+
+%!test
+%!  x = ones(3,1);
+%!  y = ones(1,3);
+%!  b = 2;
+%!  c = 3;
+%!  assert (conv (x, x), [1; 2; 3; 2; 1]);
+%!  assert (conv (y, y), [1, 2, 3, 2, 1]);
+%!  assert (conv (x, y), [1, 2, 3, 2, 1]);
+%!  assert (conv (y, x), [1; 2; 3; 2; 1]);
+%!  assert (conv (c, x), [3; 3; 3]);
+%!  assert (conv (c, y), [3, 3, 3]);
+%!  assert (conv (x, c), [3; 3; 3]);
+%!  assert (conv (y, c), [3, 3, 3]);
+%!  assert (conv (b, c), 6);
+
+%!test
+%!  a = 1:10;
+%!  b = 1:3;
+%!  assert (size (conv(a,b)), [1, numel(a)+numel(b)-1]);
+%!  assert (size (conv(b,a)), [1, numel(a)+numel(b)-1]);
+
+%!test
+%!  a = (1:10).';
+%!  b = 1:3;
+%!  assert (size (conv(a,b)), [numel(a)+numel(b)-1, 1]);
+%!  assert (size (conv(b,a)), [numel(a)+numel(b)-1, 1]);
+
+%!test
+%!  a = 1:10;
+%!  b = (1:3).';
+%!  assert (size (conv(a,b)), [1, numel(a)+numel(b)-1]);
+%!  assert (size (conv(b,a)), [1, numel(a)+numel(b)-1]);
+
+%!test
+%!  a = 1:10;
+%!  b = 1:3;
+%!  assert (conv (a,b,"full"), conv (a,b));
+%!  assert (conv (b,a,"full"), conv (b,a));
+
+%!test
+%!  a = 1:10;
+%!  b = 1:3;
+%!  assert (conv (a,b,"same"), [4, 10, 16, 22, 28, 34, 40, 46, 52, 47]);
+%!  assert (conv (b,a,"same"), [28, 34, 40]);
+
+%% Test input validation
+%!error conv (1)
+%!error conv (1,2,3,4)
+%!error conv ([1, 2; 3, 4], 3)
+%!error conv (3, [1, 2; 3, 4])
+%!error conv (2, 3, "XXXX")
+