home *** CD-ROM | disk | FTP | other *** search
/ Geek Gadgets 1 / ADE-1.bin / ade-dist / octave-1.1.1p1-base.tgz / octave-1.1.1p1-base.tar / fsf / octave / src / data.cc < prev    next >
C/C++ Source or Header  |  1995-02-22  |  19KB  |  1,040 lines

  1. // data.cc                                               -*- C++ -*-
  2. /*
  3.  
  4. Copyright (C) 1992, 1993, 1994, 1995 John W. Eaton
  5.  
  6. This file is part of Octave.
  7.  
  8. Octave is free software; you can redistribute it and/or modify it
  9. under the terms of the GNU General Public License as published by the
  10. Free Software Foundation; either version 2, or (at your option) any
  11. later version.
  12.  
  13. Octave is distributed in the hope that it will be useful, but WITHOUT
  14. ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  15. FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  16. for more details.
  17.  
  18. You should have received a copy of the GNU General Public License
  19. along with Octave; see the file COPYING.  If not, write to the Free
  20. Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  21.  
  22. */
  23.  
  24. /*
  25.  
  26. The function builtin_pwd adapted from a similar function from GNU
  27. Bash, the Bourne Again SHell, copyright (C) 1987, 1989, 1991 Free
  28. Software Foundation, Inc.
  29.  
  30. */
  31.  
  32. #ifdef HAVE_CONFIG_H
  33. #include "config.h"
  34. #endif
  35.  
  36. #include "tree-const.h"
  37. #include "user-prefs.h"
  38. #include "help.h"
  39. #include "utils.h"
  40. #include "error.h"
  41. #include "gripes.h"
  42. #include "defun.h"
  43.  
  44. #ifndef MIN
  45. #define MIN(a,b) ((a) < (b) ? (a) : (b))
  46. #endif
  47.  
  48. #ifndef ABS
  49. #define ABS(x) (((x) < 0) ? (-x) : (x))
  50. #endif
  51.  
  52. DEFUN ("all", Fall, Sall, 1, 1,
  53.   "all (X): are all elements of X nonzero?")
  54. {
  55.   Octave_object retval;
  56.  
  57.   int nargin = args.length ();
  58.  
  59.   if (nargin == 1 && args(0).is_defined ())
  60.     retval = args(0).all ();
  61.   else
  62.     print_usage ("all");
  63.  
  64.   return retval;
  65. }
  66.  
  67. DEFUN ("any", Fany, Sany, 1, 1,
  68.   "any (X): are any elements of X nonzero?")
  69. {
  70.   Octave_object retval;
  71.  
  72.   int nargin = args.length ();
  73.  
  74.   if (nargin == 1 && args(0).is_defined ())
  75.     retval = args(0).any ();
  76.   else
  77.     print_usage ("any");
  78.  
  79.   return retval;
  80. }
  81.  
  82. // These mapping functions may also be useful in other places, eh?
  83.  
  84. typedef double (*d_dd_fcn) (double, double);
  85.  
  86. static Matrix
  87. map (d_dd_fcn f, double x, const Matrix& y)
  88. {
  89.   int nr = y.rows ();
  90.   int nc = y.columns ();
  91.  
  92.   Matrix retval (nr, nc);
  93.  
  94.   for (int j = 0; j < nc; j++)
  95.     for (int i = 0; i < nr; i++)
  96.       retval.elem (i, j) = f (x, y.elem (i, j));
  97.  
  98.   return retval;
  99. }
  100.  
  101. static Matrix
  102. map (d_dd_fcn f, const Matrix& x, double y)
  103. {
  104.   int nr = x.rows ();
  105.   int nc = x.columns ();
  106.  
  107.   Matrix retval (nr, nc);
  108.  
  109.   for (int j = 0; j < nc; j++)
  110.     for (int i = 0; i < nr; i++)
  111.       retval.elem (i, j) = f (x.elem (i, j), y);
  112.  
  113.   return retval;
  114. }
  115.  
  116. static Matrix
  117. map (d_dd_fcn f, const Matrix& x, const Matrix& y)
  118. {
  119.   int x_nr = x.rows ();
  120.   int x_nc = x.columns ();
  121.  
  122.   int y_nr = y.rows ();
  123.   int y_nc = y.columns ();
  124.  
  125.   assert (x_nr == y_nr && x_nc == y_nc);
  126.  
  127.   Matrix retval (x_nr, x_nc);
  128.  
  129.   for (int j = 0; j < x_nc; j++)
  130.     for (int i = 0; i < x_nr; i++)
  131.       retval.elem (i, j) = f (x.elem (i, j), y.elem (i, j));
  132.  
  133.   return retval;
  134. }
  135.  
  136. DEFUN ("atan2", Fatan2, Satan2, 2, 1,
  137.   "atan2 (Y, X): atan (Y / X) in range -pi to pi")
  138. {
  139.   Octave_object retval;
  140.  
  141.   int nargin = args.length ();
  142.  
  143.   if (nargin == 2 && args(0).is_defined () && args(1).is_defined ())
  144.     {
  145.       tree_constant arg_y = args(0);
  146.       tree_constant arg_x = args(1);
  147.  
  148.       int y_nr = arg_y.rows ();
  149.       int y_nc = arg_y.columns ();
  150.  
  151.       int x_nr = arg_x.rows ();
  152.       int x_nc = arg_x.columns ();
  153.  
  154.       int arg_y_empty = empty_arg ("atan2", y_nr, y_nc);
  155.       int arg_x_empty = empty_arg ("atan2", x_nr, x_nc);
  156.  
  157.       if (arg_y_empty > 0 && arg_x_empty > 0)
  158.     return Matrix ();
  159.       else if (arg_y_empty || arg_x_empty)
  160.     return retval;
  161.  
  162.       int y_is_scalar = (y_nr == 1 && y_nc == 1);
  163.       int x_is_scalar = (x_nr == 1 && x_nc == 1);
  164.  
  165.       if (y_is_scalar && x_is_scalar)
  166.     {
  167.       double y = arg_y.double_value ();
  168.  
  169.       if (! error_state)
  170.         {
  171.           double x = arg_x.double_value ();
  172.  
  173.           if (! error_state)
  174.         retval = atan2 (y, x);
  175.         }
  176.     }
  177.       else if (y_is_scalar)
  178.     {
  179.       double y = arg_y.double_value ();
  180.  
  181.       if (! error_state)
  182.         {
  183.           Matrix x = arg_x.matrix_value ();
  184.  
  185.           if (! error_state)
  186.         retval = map (atan2, y, x);
  187.         }
  188.     }
  189.       else if (x_is_scalar)
  190.     {
  191.       Matrix y = arg_y.matrix_value ();
  192.  
  193.       if (! error_state)
  194.         {
  195.           double x = arg_x.double_value ();
  196.  
  197.           if (! error_state)
  198.         retval = map (atan2, y, x);
  199.         }
  200.     }
  201.       else if (y_nr == x_nr && y_nc == x_nc)
  202.     {
  203.       Matrix y = arg_y.matrix_value ();
  204.  
  205.       if (! error_state)
  206.         {
  207.           Matrix x = arg_x.matrix_value ();
  208.  
  209.           if (! error_state)
  210.         retval = map (atan2, y, x);
  211.         }
  212.     }
  213.       else
  214.     error ("atan2: nonconformant matrices");
  215.     }
  216.   else
  217.     print_usage ("atan2");
  218.  
  219.   return retval;
  220. }
  221.  
  222. DEFUN ("cumprod", Fcumprod, Scumprod, 1, 1,
  223.   "cumprod (X): cumulative products")
  224. {
  225.   Octave_object retval;
  226.  
  227.   int nargin = args.length ();
  228.  
  229.   if (nargin == 1)
  230.     {
  231.       tree_constant arg = args(0);
  232.  
  233.       if (arg.is_real_type ())
  234.     {
  235.       Matrix tmp = arg.matrix_value ();
  236.  
  237.       if (! error_state)
  238.         retval(0) = tmp.cumprod ();
  239.     }
  240.       else if (arg.is_complex_type ())
  241.     {
  242.       ComplexMatrix tmp = arg.complex_matrix_value ();
  243.  
  244.       if (! error_state)
  245.         retval(0) = tmp.cumprod ();
  246.     }
  247.       else
  248.     {
  249.       gripe_wrong_type_arg ("cumprod", arg);
  250.       return retval;
  251.     }
  252.     }
  253.   else
  254.     print_usage ("cumprod");
  255.  
  256.   return retval;
  257. }
  258.  
  259. DEFUN ("cumsum", Fcumsum, Scumsum, 1, 1,
  260.   "cumsum (X): cumulative sums")
  261. {
  262.   Octave_object retval;
  263.  
  264.   int nargin = args.length ();
  265.  
  266.   if (nargin == 1)
  267.     {
  268.       tree_constant arg = args(0);
  269.  
  270.       if (arg.is_real_type ())
  271.     {
  272.       Matrix tmp = arg.matrix_value ();
  273.  
  274.       if (! error_state)
  275.         retval(0) = tmp.cumsum ();
  276.     }
  277.       else if (arg.is_complex_type ())
  278.     {
  279.       ComplexMatrix tmp = arg.complex_matrix_value ();
  280.  
  281.       if (! error_state)
  282.         retval(0) = tmp.cumsum ();
  283.     }
  284.       else
  285.     {
  286.       gripe_wrong_type_arg ("cumsum", arg);
  287.       return retval;
  288.     }
  289.     }
  290.   else
  291.     print_usage ("cumsum");
  292.  
  293.   return retval;
  294. }
  295.  
  296. static tree_constant
  297. make_diag (const Matrix& v, int k)
  298. {
  299.   int nr = v.rows ();
  300.   int nc = v.columns ();
  301.   assert (nc == 1 || nr == 1);
  302.  
  303.   tree_constant retval;
  304.  
  305.   int roff = 0;
  306.   int coff = 0;
  307.   if (k > 0)
  308.     {
  309.       roff = 0;
  310.       coff = k;
  311.     }
  312.   else if (k < 0)
  313.     {
  314.       roff = -k;
  315.       coff = 0;
  316.     }
  317.  
  318.   if (nr == 1)
  319.     {
  320.       int n = nc + ABS (k);
  321.       Matrix m (n, n, 0.0);
  322.       for (int i = 0; i < nc; i++)
  323.     m.elem (i+roff, i+coff) = v.elem (0, i);
  324.       retval = tree_constant (m);
  325.     }
  326.   else
  327.     {
  328.       int n = nr + ABS (k);
  329.       Matrix m (n, n, 0.0);
  330.       for (int i = 0; i < nr; i++)
  331.     m.elem (i+roff, i+coff) = v.elem (i, 0);
  332.       retval = tree_constant (m);
  333.     }
  334.  
  335.   return retval;
  336. }
  337.  
  338. static tree_constant
  339. make_diag (const ComplexMatrix& v, int k)
  340. {
  341.   int nr = v.rows ();
  342.   int nc = v.columns ();
  343.   assert (nc == 1 || nr == 1);
  344.  
  345.   tree_constant retval;
  346.  
  347.   int roff = 0;
  348.   int coff = 0;
  349.   if (k > 0)
  350.     {
  351.       roff = 0;
  352.       coff = k;
  353.     }
  354.   else if (k < 0)
  355.     {
  356.       roff = -k;
  357.       coff = 0;
  358.     }
  359.  
  360.   if (nr == 1)
  361.     {
  362.       int n = nc + ABS (k);
  363.       ComplexMatrix m (n, n, 0.0);
  364.       for (int i = 0; i < nc; i++)
  365.     m.elem (i+roff, i+coff) = v.elem (0, i);
  366.       retval = tree_constant (m);
  367.     }
  368.   else
  369.     {
  370.       int n = nr + ABS (k);
  371.       ComplexMatrix m (n, n, 0.0);
  372.       for (int i = 0; i < nr; i++)
  373.     m.elem (i+roff, i+coff) = v.elem (i, 0);
  374.       retval = tree_constant (m);
  375.     }
  376.  
  377.   return retval;
  378. }
  379.  
  380. static tree_constant
  381. make_diag (const tree_constant& arg)
  382. {
  383.   tree_constant retval;
  384.  
  385.   if (arg.is_real_type ())
  386.     {
  387.       Matrix m = arg.matrix_value ();
  388.  
  389.       if (! error_state)
  390.     {
  391.       int nr = m.rows ();
  392.       int nc = m.columns ();
  393.  
  394.       if (nr == 0 || nc == 0)
  395.         retval = Matrix ();
  396.       else if (nr == 1 || nc == 1)
  397.         retval = make_diag (m, 0);
  398.       else
  399.         {
  400.           ColumnVector v = m.diag ();
  401.           if (v.capacity () > 0)
  402.         retval = v;
  403.         }
  404.     }
  405.       else
  406.     gripe_wrong_type_arg ("diag", arg);
  407.     }
  408.   else if (arg.is_complex_type ())
  409.     {
  410.       ComplexMatrix cm = arg.complex_matrix_value ();
  411.  
  412.       if (! error_state)
  413.     {
  414.       int nr = cm.rows ();
  415.       int nc = cm.columns ();
  416.  
  417.       if (nr == 0 || nc == 0)
  418.         retval = Matrix ();
  419.       else if (nr == 1 || nc == 1)
  420.         retval = make_diag (cm, 0);
  421.       else
  422.         {
  423.           ComplexColumnVector v = cm.diag ();
  424.           if (v.capacity () > 0)
  425.         retval = v;
  426.         }
  427.     }
  428.       else
  429.     gripe_wrong_type_arg ("diag", arg);
  430.     }
  431.   else
  432.     gripe_wrong_type_arg ("diag", arg);
  433.  
  434.   return retval;
  435. }
  436.  
  437. static tree_constant
  438. make_diag (const tree_constant& a, const tree_constant& b)
  439. {
  440.   tree_constant retval;
  441.  
  442.   double tmp = b.double_value ();
  443.  
  444.   if (error_state)
  445.     {
  446.       error ("diag: invalid second argument");      
  447.       return retval;
  448.     }
  449.  
  450.   int k = NINT (tmp);
  451.   int n = ABS (k) + 1;
  452.  
  453.   if (a.is_real_type ())
  454.     {
  455.       if (a.is_scalar_type ())
  456.     {
  457.       double d = a.double_value ();
  458.  
  459.       if (k == 0)
  460.         retval = d;
  461.       else if (k > 0)
  462.         {
  463.           Matrix m (n, n, 0.0);
  464.           m.elem (0, k) = d;
  465.           retval = m;
  466.         }
  467.       else if (k < 0)
  468.         {
  469.           Matrix m (n, n, 0.0);
  470.           m.elem (-k, 0) = d;
  471.           retval = m;
  472.         }
  473.     }
  474.       else if (a.is_matrix_type ())
  475.     {
  476.       Matrix m = a.matrix_value ();
  477.  
  478.       int nr = m.rows ();
  479.       int nc = m.columns ();
  480.  
  481.       if (nr == 0 || nc == 0)
  482.         retval = Matrix ();
  483.       else if (nr == 1 || nc == 1)
  484.         retval = make_diag (m, k);
  485.       else
  486.         {
  487.           ColumnVector d = m.diag (k);
  488.           retval = d;
  489.         }
  490.     }
  491.       else
  492.     gripe_wrong_type_arg ("diag", a);
  493.     }
  494.   else if (a.is_complex_type ())
  495.     {
  496.       if (a.is_scalar_type ())
  497.     {
  498.       Complex c = a.complex_value ();
  499.  
  500.       if (k == 0)
  501.         retval = c;
  502.       else if (k > 0)
  503.         {
  504.           ComplexMatrix m (n, n, 0.0);
  505.           m.elem (0, k) = c;
  506.           retval = m;
  507.         }
  508.       else if (k < 0)
  509.         {
  510.           ComplexMatrix m (n, n, 0.0);
  511.           m.elem (-k, 0) = c;
  512.           retval = m;
  513.         }
  514.     }
  515.       else if (a.is_matrix_type ())
  516.     {
  517.       ComplexMatrix cm = a.complex_matrix_value ();
  518.  
  519.       int nr = cm.rows ();
  520.       int nc = cm.columns ();
  521.  
  522.       if (nr == 0 || nc == 0)
  523.         retval = Matrix ();
  524.       else if (nr == 1 || nc == 1)
  525.         retval = make_diag (cm, k);
  526.       else
  527.         {
  528.           ComplexColumnVector d = cm.diag (k);
  529.           retval = d;
  530.         }
  531.     }
  532.       else
  533.     gripe_wrong_type_arg ("diag", a);
  534.     }
  535.   else
  536.     gripe_wrong_type_arg ("diag", a);
  537.  
  538.   return retval;
  539. }
  540.  
  541. DEFUN ("diag", Fdiag, Sdiag, 2, 1,
  542.   "diag (X [,k]): form/extract diagonals")
  543. {
  544.   Octave_object retval;
  545.  
  546.   int nargin = args.length ();
  547.  
  548.   if (nargin == 1 && args(0).is_defined ())
  549.     retval = make_diag (args(0));
  550.   else if (nargin == 2 && args(0).is_defined () && args(1).is_defined ())
  551.     retval = make_diag (args(0), args(1));
  552.   else
  553.     print_usage ("diag");
  554.  
  555.   return retval;
  556. }
  557.  
  558. DEFUN ("prod", Fprod, Sprod, 1, 1,
  559.   "prod (X): products")
  560. {
  561.   Octave_object retval;
  562.  
  563.   int nargin = args.length ();
  564.  
  565.   if (nargin == 1)
  566.     {
  567.       tree_constant arg = args(0);
  568.  
  569.       if (arg.is_real_type ())
  570.     {
  571.       Matrix tmp = arg.matrix_value ();
  572.  
  573.       if (! error_state)
  574.         retval(0) = tmp.prod ();
  575.     }
  576.       else if (arg.is_complex_type ())
  577.     {
  578.       ComplexMatrix tmp = arg.complex_matrix_value ();
  579.  
  580.       if (! error_state)
  581.         retval(0) = tmp.prod ();
  582.     }
  583.       else
  584.     {
  585.       gripe_wrong_type_arg ("prod", arg);
  586.       return retval;
  587.     }
  588.     }
  589.   else
  590.     print_usage ("prod");
  591.  
  592.   return retval;
  593. }
  594.  
  595. DEFUN ("size", Fsize, Ssize, 2, 1,
  596.   "[m, n] = size (x): return rows and columns of X\n\
  597. \n\
  598. d = size (x): return number of rows and columns of x as a row vector\n\
  599. \n\
  600. m = size (x, 1): return number of rows in x\n\
  601. m = size (x, 2): return number of columns in x")
  602. {
  603.   Octave_object retval;
  604.  
  605.   int nargin = args.length ();
  606.  
  607.   if (nargin == 1 && nargout < 3)
  608.     {
  609.       int nr = args(0).rows ();
  610.       int nc = args(0).columns ();
  611.  
  612.       if (nargout == 0 || nargout == 1)
  613.     {
  614.       Matrix m (1, 2);
  615.       m.elem (0, 0) = nr;
  616.       m.elem (0, 1) = nc;
  617.       retval = m;
  618.     }
  619.       else if (nargout == 2)
  620.     {
  621.       retval(1) = (double) nc;
  622.       retval(0) = (double) nr;
  623.     }
  624.     }
  625.   else if (nargin == 2 && nargout < 2)
  626.     {
  627.       int nd = NINT (args(1).double_value ());
  628.  
  629.       if (error_state)
  630.     error ("size: expecting scalar as second argument");
  631.       else
  632.     {
  633.       if (nd == 1)
  634.         retval(0) = (double) (args(0).rows ());
  635.       else if (nd == 2)
  636.         retval(0) = (double) (args(0).columns ());
  637.       else
  638.         error ("size: invalid second argument -- expecting 1 or 2");
  639.     }
  640.     }
  641.   else
  642.     print_usage ("size");
  643.  
  644.   return retval;
  645. }
  646.  
  647. DEFUN ("sum", Fsum, Ssum, 1, 1,
  648.   "sum (X): sum of elements")
  649. {
  650.   Octave_object retval;
  651.  
  652.   int nargin = args.length ();
  653.  
  654.   if (nargin == 1)
  655.     {
  656.       tree_constant arg = args(0);
  657.  
  658.       if (arg.is_real_type ())
  659.     {
  660.       Matrix tmp = arg.matrix_value ();
  661.  
  662.       if (! error_state)
  663.         retval(0) = tmp.sum ();
  664.     }
  665.       else if (arg.is_complex_type ())
  666.     {
  667.       ComplexMatrix tmp = arg.complex_matrix_value ();
  668.  
  669.       if (! error_state)
  670.         retval(0) = tmp.sum ();
  671.     }
  672.       else
  673.     {
  674.       gripe_wrong_type_arg ("sum", arg);
  675.       return retval;
  676.     }
  677.     }
  678.   else
  679.     print_usage ("sum");
  680.  
  681.   return retval;
  682. }
  683.  
  684. DEFUN ("sumsq", Fsumsq, Ssumsq, 1, 1,
  685.   "sumsq (X): sum of squares of elements")
  686. {
  687.   Octave_object retval;
  688.  
  689.   int nargin = args.length ();
  690.  
  691.   if (nargin == 1)
  692.     {
  693.       tree_constant arg = args(0);
  694.  
  695.       if (arg.is_real_type ())
  696.     {
  697.       Matrix tmp = arg.matrix_value ();
  698.  
  699.       if (! error_state)
  700.         retval(0) = tmp.sumsq ();
  701.     }
  702.       else if (arg.is_complex_type ())
  703.     {
  704.       ComplexMatrix tmp = arg.complex_matrix_value ();
  705.  
  706.       if (! error_state)
  707.         retval(0) = tmp.sumsq ();
  708.     }
  709.       else
  710.     {
  711.       gripe_wrong_type_arg ("sumsq", arg);
  712.       return retval;
  713.     }
  714.     }
  715.   else
  716.     print_usage ("sumsq");
  717.  
  718.   return retval;
  719. }
  720.  
  721. DEFUN ("is_struct", Fis_struct, Sis_struct, 1, 1,
  722.   "is_struct (x): return nonzero if x is a structure")
  723. {
  724.   Octave_object retval;
  725.  
  726.   int nargin = args.length ();
  727.  
  728.   if (nargin == 1)
  729.     {
  730.       tree_constant arg = args(0);
  731.  
  732.       if (arg.is_map ())
  733.     retval = 1.0;
  734.       else
  735.     retval = 0.0;
  736.     }
  737.   else
  738.     print_usage ("is_struct");
  739.  
  740.   return retval;
  741. }
  742.  
  743. static void
  744. check_dimensions (int& nr, int& nc, const char *warnfor)
  745. {
  746.   if (nr < 0 || nc < 0)
  747.     {
  748.       if (user_pref.treat_neg_dim_as_zero)
  749.     {
  750.       nr = (nr < 0) ? 0 : nr;
  751.       nc = (nc < 0) ? 0 : nc;
  752.  
  753.       if (user_pref.treat_neg_dim_as_zero < 0)
  754.         warning ("%s: converting negative dimension to zero",
  755.              warnfor);
  756.     }
  757.       else
  758.     error ("%s: can't create a matrix with negative dimensions",
  759.            warnfor);
  760.     }
  761. }
  762.  
  763. static void
  764. get_dimensions (const tree_constant& a, const char *warn_for,
  765.         int& nr, int& nc)
  766. {
  767.   if (a.is_scalar_type ())
  768.     {
  769.       double tmp = a.double_value ();
  770.       nr = nc = NINT (tmp);
  771.     }
  772.   else
  773.     {
  774.       nr = a.rows ();
  775.       nc = a.columns ();
  776.  
  777.       if ((nr == 1 && nc == 2) || (nr == 2 && nc == 1))
  778.     {
  779.       ColumnVector v = a.vector_value ();
  780.  
  781.       if (error_state)
  782.         return;
  783.  
  784.       nr = NINT (v.elem (0));
  785.       nc = NINT (v.elem (1));
  786.     }
  787.       else
  788.     warning ("%s (A): use %s (size (A)) instead", warn_for, warn_for);
  789.     }
  790.  
  791.   check_dimensions (nr, nc, warn_for); // May set error_state.
  792. }
  793.  
  794. static void
  795. get_dimensions (const tree_constant& a, const tree_constant& b,
  796.         const char *warn_for, int& nr, int& nc)
  797. {
  798.   nr = NINT (a.double_value ());
  799.   nc = NINT (b.double_value ());
  800.  
  801.   if (error_state)
  802.     error ("%s: expecting two scalar arguments", warn_for);
  803.   else
  804.     check_dimensions (nr, nc, warn_for); // May set error_state.
  805. }
  806.  
  807. static tree_constant
  808. fill_matrix (const tree_constant& a, double val, const char *warn_for)
  809. {
  810.   int nr, nc;
  811.   get_dimensions (a, warn_for, nr, nc);
  812.  
  813.   if (error_state)
  814.     return  tree_constant ();
  815.  
  816.   Matrix m (nr, nc, val);
  817.  
  818.   return m;
  819. }
  820.  
  821. static tree_constant
  822. fill_matrix (const tree_constant& a, const tree_constant& b,
  823.          double val, const char *warn_for)
  824. {
  825.   int nr, nc;
  826.   get_dimensions (a, b, warn_for, nr, nc); // May set error_state.
  827.  
  828.   if (error_state)
  829.     return tree_constant ();
  830.  
  831.   Matrix m (nr, nc, val);
  832.  
  833.   return m;
  834. }
  835.  
  836. DEFUN ("ones", Fones, Sones, 2, 1,
  837.   "ones (N), ones (N, M), ones (X): create a matrix of all ones")
  838. {
  839.   Octave_object retval;
  840.  
  841.   int nargin = args.length ();
  842.  
  843.   switch (nargin)
  844.     {
  845.     case 0:
  846.       retval = 1.0;
  847.       break;
  848.  
  849.     case 1:
  850.       retval = fill_matrix (args(0), 1.0, "ones");
  851.       break;
  852.  
  853.     case 2:
  854.       retval = fill_matrix (args(0), args(1), 1.0, "ones");
  855.       break;
  856.  
  857.     default:
  858.       print_usage ("ones");
  859.       break;
  860.     }
  861.  
  862.   return retval;
  863. }
  864.  
  865. DEFUN ("zeros", Fzeros, Szeros, 2, 1,
  866.   "zeros (N), zeros (N, M), zeros (X): create a matrix of all zeros")
  867. {
  868.   Octave_object retval;
  869.  
  870.   int nargin = args.length ();
  871.  
  872.   switch (nargin)
  873.     {
  874.     case 0:
  875.       retval = 0.0;
  876.       break;
  877.  
  878.     case 1:
  879.       retval = fill_matrix (args(0), 0.0, "zeros");
  880.       break;
  881.  
  882.     case 2:
  883.       retval = fill_matrix (args(0), args(1), 0.0, "zeros");
  884.       break;
  885.  
  886.     default:
  887.       print_usage ("zeros");
  888.       break;
  889.     }
  890.  
  891.   return retval;
  892. }
  893.  
  894. static tree_constant
  895. identity_matrix (const tree_constant& a)
  896. {
  897.   int nr, nc;
  898.   get_dimensions (a, "eye", nr, nc); // May set error_state.
  899.  
  900.   if (error_state)
  901.     return tree_constant ();
  902.  
  903.   Matrix m (nr, nc, 0.0);
  904.  
  905.   if (nr > 0 && nc > 0)
  906.     {
  907.       int n = MIN (nr, nc);
  908.       for (int i = 0; i < n; i++)
  909.     m.elem (i, i) = 1.0;
  910.     }
  911.  
  912.   return m;
  913. }
  914.  
  915. static tree_constant
  916. identity_matrix (const tree_constant& a, const tree_constant& b)
  917. {
  918.   int nr, nc;
  919.   get_dimensions (a, b, "eye", nr, nc);  // May set error_state.
  920.  
  921.   if (error_state)
  922.     return tree_constant ();
  923.  
  924.   Matrix m (nr, nc, 0.0);
  925.  
  926.   if (nr > 0 && nc > 0)
  927.     {
  928.       int n = MIN (nr, nc);
  929.       for (int i = 0; i < n; i++)
  930.     m.elem (i, i) = 1.0;
  931.     }
  932.  
  933.   return m;
  934. }
  935.  
  936. DEFUN ("eye", Feye, Seye, 2, 1,
  937.   "eye (N), eye (N, M), eye (X): create an identity matrix")
  938. {
  939.   Octave_object retval;
  940.  
  941.   int nargin = args.length ();
  942.  
  943.   switch (nargin)
  944.     {
  945.     case 0:
  946.       retval = 1.0;
  947.       break;
  948.  
  949.     case 1:
  950.       retval = identity_matrix (args(0));
  951.       break;
  952.  
  953.     case 2:
  954.       retval = identity_matrix (args(0), args(1));
  955.       break;
  956.  
  957.     default:
  958.       print_usage ("eye");
  959.       break;
  960.     }
  961.  
  962.   return retval;
  963. }
  964.  
  965. DEFUN ("linspace", Flinspace, Slinspace, 2, 1,
  966.   "usage: linspace (x1, x2, n)\n\
  967. \n\
  968. Return a vector of n equally spaced points between x1 and x2\n\
  969. inclusive.\n\
  970. \n\
  971. If the final argument is omitted, n = 100 is assumed.\n\
  972. \n\
  973. All three arguments must be scalars.\n\
  974. \n\
  975. See also: logspace")
  976. {
  977.   Octave_object retval;
  978.  
  979.   int nargin = args.length ();
  980.  
  981.   int npoints = 100;
  982.  
  983.   if (nargin == 3)
  984.     {
  985.       double n = args(2).double_value ();
  986.  
  987.       if (! error_state)
  988.     npoints = NINT (n);
  989.     }
  990.   else
  991.     print_usage ("linspace");
  992.  
  993.   if (! error_state)
  994.     {
  995.       if (npoints > 1)
  996.     {
  997.       tree_constant arg_1 = args(0);
  998.       tree_constant arg_2 = args(1);
  999.  
  1000.       if (arg_1.is_complex_type () || arg_2.is_complex_type ())
  1001.         {
  1002.           Complex x1 = arg_1.complex_value ();
  1003.           Complex x2 = arg_2.complex_value ();
  1004.  
  1005.           if (! error_state)
  1006.         {
  1007.           ComplexRowVector rv = linspace (x1, x2, npoints);
  1008.  
  1009.           if (! error_state)
  1010.             retval (0) = tree_constant (rv, 0);
  1011.         }
  1012.         }
  1013.       else
  1014.         {
  1015.           double x1 = arg_1.double_value ();
  1016.           double x2 = arg_2.double_value ();
  1017.  
  1018.           if (! error_state)
  1019.         {
  1020.           RowVector rv = linspace (x1, x2, npoints);
  1021.  
  1022.           if (! error_state)
  1023.             retval (0) = tree_constant (rv, 0);
  1024.         }
  1025.         }
  1026.     }
  1027.       else
  1028.     error ("linspace: npoints must be greater than 2");
  1029.     }
  1030.  
  1031.   return retval;
  1032. }
  1033.  
  1034. /*
  1035. ;;; Local Variables: ***
  1036. ;;; mode: C++ ***
  1037. ;;; page-delimiter: "^/\\*" ***
  1038. ;;; End: ***
  1039. */
  1040.