# HG changeset patch # User David Bateman # Date 1206042859 -3600 # Node ID 3209a584e1ace4dbfdcd9b6f0cab03b43fe2c0c3 # Parent 9dca8b03dfe8ea5216d781b0bd63557970145a91 Further type preservation tests and fix of diag for cell arrays diff --git a/scripts/ChangeLog b/scripts/ChangeLog --- a/scripts/ChangeLog +++ b/scripts/ChangeLog @@ -1,5 +1,7 @@ 2008-03-20 David Bateman + * general/tril.m, general/triu.m: Fail if input is a structure. + * miscellaneous/cast.m: Also allow cast to "char". * general/rotdim.m: Ensure k is an integer scale. diff --git a/scripts/general/tril.m b/scripts/general/tril.m --- a/scripts/general/tril.m +++ b/scripts/general/tril.m @@ -67,8 +67,10 @@ function retval = tril (x, k) if (nargin > 0) + if (isstruct (x)) + error ("tril: structure arrays not supported"); + endif [nr, nc] = size (x); - retval = resize (resize (x, 0), nr, nc); endif if (nargin == 1) @@ -81,6 +83,7 @@ print_usage (); endif + retval = resize (resize (x, 0), nr, nc); for j = 1 : min (nc, nr+k) nr_limit = max (1, j-k); retval (nr_limit:nr, j) = x (nr_limit:nr, j); diff --git a/scripts/general/triu.m b/scripts/general/triu.m --- a/scripts/general/triu.m +++ b/scripts/general/triu.m @@ -27,10 +27,11 @@ function retval = triu (x, k) if (nargin > 0) + if (isstruct (x)) + error ("tril: structure arrays not supported"); + endif [nr, nc] = size (x); - retval = resize (resize (x, 0), nr, nc); endif - if (nargin == 1) k = 0; elseif (nargin == 2) @@ -41,6 +42,7 @@ print_usage (); endif + retval = resize (resize (x, 0), nr, nc); for j = max (1, k+1) : nc nr_limit = min (nr, j-k); retval (1:nr_limit, j) = x (1:nr_limit, j); diff --git a/src/Cell.cc b/src/Cell.cc --- a/src/Cell.cc +++ b/src/Cell.cc @@ -238,6 +238,52 @@ return retval; } +Cell +Cell::diag (void) const +{ + return diag (0); +} + +Cell +Cell::diag (octave_idx_type k) const +{ + octave_idx_type nnr = rows (); + octave_idx_type nnc = cols (); + if (k > 0) + nnc -= k; + else if (k < 0) + nnr += k; + + Cell d; + + if (nnr > 0 && nnc > 0) + { + octave_idx_type ndiag = (nnr < nnc) ? nnr : nnc; + + d.resize (dim_vector (ndiag, 1)); + + if (k > 0) + { + for (octave_idx_type i = 0; i < ndiag; i++) + d.elem (i) = elem (i, i+k); + } + else if (k < 0) + { + for (octave_idx_type i = 0; i < ndiag; i++) + d.elem (i) = elem (i-k, i); + } + else + { + for (octave_idx_type i = 0; i < ndiag; i++) + d.elem (i) = elem (i, i); + } + } + else + error ("diag: requested diagonal out of range"); + + return d; +} + /* ;;; Local Variables: *** ;;; mode: C++ *** diff --git a/src/Cell.h b/src/Cell.h --- a/src/Cell.h +++ b/src/Cell.h @@ -115,6 +115,9 @@ static octave_value resize_fill_value (void) { return Matrix (); } + Cell diag (void) const; + Cell diag (octave_idx_type k) const; + Cell xisalnum (void) const { return map (&octave_value::xisalnum); } Cell xisalpha (void) const { return map (&octave_value::xisalpha); } Cell xisascii (void) const { return map (&octave_value::xisascii); } diff --git a/src/ChangeLog b/src/ChangeLog --- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,15 @@ +2008-03-20 David Bateman + + * data.cc (static octave_value make_diag (const Cell&, + octave_idx_type)): New instantiation of template function. + (static octave_value make_diag (const octave_value&, + octave_idx_type)): Allow cell arrays. + + * Cell.cc (Cell Cell::diag (void) const, Cell Cell::diag + (octave__idx_type)): New methods for diagonal matrices. + * Cell.h (Cell Cell::diag (void) const, Cell Cell::diag + (octave__idx_type)): Declare them. + 2008-03-18 David Bateman * ov-re-mat.cc (lgamma): Convert to a allow negative arguments. diff --git a/src/data.cc b/src/data.cc --- a/src/data.cc +++ b/src/data.cc @@ -976,6 +976,9 @@ static octave_value make_diag (const uint64NDArray& v, octave_idx_type k); + +static octave_value +make_diag (const Cell& v, octave_idx_type k); #endif template @@ -1150,6 +1153,8 @@ retval = make_diag (a.uint32_array_value (), k); else if (result_type == "uint64") retval = make_diag (a.uint64_array_value (), k); + else if (result_type == "cell") + retval = make_diag (a.cell_value (), k); else gripe_wrong_type_arg ("diag", a); diff --git a/test/ChangeLog b/test/ChangeLog --- a/test/ChangeLog +++ b/test/ChangeLog @@ -1,5 +1,7 @@ 2008-03-20 David Bateman + * test_func.m: Modify to test for char, cell and structure arrays. + * test_func.m: New test code that ensures that all operations which work on dimensions alone (squeeze, triu, etc.) work for all objects and preserve type. diff --git a/test/test_func.m b/test/test_func.m --- a/test/test_func.m +++ b/test/test_func.m @@ -22,34 +22,29 @@ ## not to check that the function itself returns teh correct result, ## just that the results are consistent for all types. -%!function __fntestfunc__ (fn, min, varargin) +%!function __fntestfunc__ (fn, mn, varargin) %! typ = {'double', 'complex', 'logical', 'sparse', 'complex sparse', ... %! 'logical sparse', 'int8', 'int16', 'int32', 'int64', 'uint8', ... -%! 'uint16', 'uint32', 'uint64'}; +%! 'uint16', 'uint32', 'uint64', 'char', 'cell', 'struct'}; %! %! cmplx = [2, 5]; %! nlogical = [3, 6]; %! ninteger = [7, 8, 9, 10, 11, 12, 13, 14]; %! nsparse = [4, 5, 6]; -%! usesparse = true; +%! skip = {}; %! -%! if (length (varargin) > 0 && islogical (varargin{1})) -%! usesparse = varargin{1}; +%! if (length (varargin) > 0 && iscell (varargin{1})) +%! skip = varargin{1}; %! varargin(1) = []; %! endif %! %! for i = 1 : length(typ) -%! m = min; -%! if (length (varargin) > 0) -%! args = varargin(1); -%! else -%! args = {}; +%! if (any (strcmp (skip, typ {i}))) +%! continue; %! endif +%! m = mn; %! %! if (any (nsparse == i)) -%! if (! usesparse) -%! continue; -%! endif %! if (ndims (m) > 2) %! sz = size (m); %! m = reshape (m, [sz(1), prod(sz (2:end))]); @@ -70,12 +65,21 @@ %! if (any (ninteger == i)) %! m = cast (m, typ{i}); %! endif +%! if (strcmp (typ{i}, 'cell')) +%! m = num2cell (m); +%! elseif (strcmp (typ{i}, 'struct')) +%! m = struct ('fld', num2cell (m)); +%! endif %! -%! y = feval (fn, m, args{:}); +%! y = feval (fn, m, varargin{:}); +%! y2 = feval (fn, reshape (mn, size (m)), varargin{:}); %! if (!strcmp (class (y), class (m)) || -%! issparse (y) != issparse (m) || -%! any (cast (real (y), 'double')(:) != -%! feval (fn , cast (real (m), 'double'), args{:})(:))) +%! issparse (y) != issparse (m) || !size_equal (y, y2)) +%! error ('failed for type %s\n', typ{i}); +%! endif +%! if (!(strcmp (typ{i}, 'cell') || strcmp (typ{i}, 'struct')) && +%! any (vec (cast (real (y), 'double')) != +%! vec (feval (fn , cast (real (m), 'double'), varargin{:})))) %! error ('failed for type %s\n', typ{i}); %! endif %! endfor @@ -88,21 +92,21 @@ %! m3 = []; %!test -%! __fntestfunc__('triu', m1); +%! __fntestfunc__('triu', m1, {'struct'}); %!test -%! __fntestfunc__ ('triu', m1, -1); +%! __fntestfunc__ ('triu', m1, {'struct'}, -1); %!test -%! __fntestfunc__ ('triu', m1, 1); +%! __fntestfunc__ ('triu', m1, {'struct'}, 1); %!test -%! __fntestfunc__('triu', m3); +%! __fntestfunc__('triu', m3, {'struct'}); %!test -%! __fntestfunc__ ('tril', m1); +%! __fntestfunc__ ('tril', m1, {'struct'}); %!test -%! __fntestfunc__ ('tril', m1, -1); +%! __fntestfunc__ ('tril', m1, {'struct'}, -1); %!test -%! __fntestfunc__ ('tril', m1, 1); +%! __fntestfunc__ ('tril', m1, {'struct'}, 1); %!test -%! __fntestfunc__('tril', m3); +%! __fntestfunc__('tril', m3, {'struct'}); %!test %! __fntestfunc__ ('squeeze', m2); %!test @@ -110,19 +114,19 @@ %!test %! __fntestfunc__ ('permute', m1, [2, 1]); %!test -%! __fntestfunc__ ('permute', m2, false, [3, 1, 2]); +%! __fntestfunc__ ('permute', m2, {'sparse', 'logical sparse', 'complex sparse'}, [3, 1, 2]); %!test %! __fntestfunc__ ('permute', m3, [2, 1]); %!test %! __fntestfunc__ ('ipermute', m1, [2, 1]); %!test -%! __fntestfunc__ ('ipermute', m2, false, [3, 1, 2]); +%! __fntestfunc__ ('ipermute', m2, {'sparse', 'logical sparse', 'complex sparse'}, [3, 1, 2]); %!test %! __fntestfunc__ ('ipermute', m3, [2, 1]); %!test %! __fntestfunc__ ('shiftdim', m2, 1); %!test -%! __fntestfunc__ ('shiftdim', m2, false, -1); +%! __fntestfunc__ ('shiftdim', m2, {'sparse', 'logical sparse', 'complex sparse'}, -1); %!test %! __fntestfunc__ ('shiftdim', m3, 1); %!test @@ -136,19 +140,19 @@ %!test %! __fntestfunc__ ('reshape', m3, [1, 0]); %!test -%! __fntestfunc__ ('diag', m0); +%! __fntestfunc__ ('diag', m0, {'struct'}); %!test -%! __fntestfunc__ ('diag', m0, 1); +%! __fntestfunc__ ('diag', m0, {'struct'}, 1); %!test -%! __fntestfunc__ ('diag', m0, -1); +%! __fntestfunc__ ('diag', m0, {'struct'}, -1); %!test -%! __fntestfunc__ ('diag', m1); +%! __fntestfunc__ ('diag', m1, {'struct'}); %!test -%! __fntestfunc__ ('diag', m1, 1); +%! __fntestfunc__ ('diag', m1, {'struct'}, 1); %!test -%! __fntestfunc__ ('diag', m1, -1); +%! __fntestfunc__ ('diag', m1, {'struct'}, -1); %!test -%! __fntestfunc__ ('diag', m3); +%! __fntestfunc__ ('diag', m3, {'struct'}); %!test %! __fntestfunc__ ('fliplr', m1); %!test