diff src/minmax.cc @ 515:e078f05f4aac

[project @ 1994-07-13 02:31:31 by jwe] Initial revision
author jwe
date Wed, 13 Jul 1994 02:31:31 +0000
parents
children b9284136189a
line wrap: on
line diff
new file mode 100644
--- /dev/null
+++ b/src/minmax.cc
@@ -0,0 +1,495 @@
+// f-minmax.cc                                           -*- C++ -*-
+/*
+
+Copyright (C) 1994 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 2, 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, write to the Free
+Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
+
+*/
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <math.h>
+
+#include "tree-const.h"
+#include "error.h"
+#include "f-minmax.h"
+
+#ifndef MAX
+#define MAX(a,b) ((a) > (b) ? (a) : (b))
+#endif
+
+#ifndef MIN
+#define MIN(a,b) ((a) < (b) ? (a) : (b))
+#endif
+
+static Matrix
+min (const Matrix& a, const Matrix& b)
+{
+  int nr = a.rows ();
+  int nc = a.columns ();
+  if (nr != b.rows () || nc != b.columns ())
+    {
+      error ("two-arg min expecting args of same size");
+      return Matrix ();
+    }
+
+  Matrix result (nr, nc);
+
+  for (int j = 0; j < nc; j++)
+    for (int i = 0; i < nr; i++)
+      {
+	double a_elem = a.elem (i, j);
+	double b_elem = b.elem (i, j);
+	result.elem (i, j) = MIN (a_elem, b_elem);
+      }
+
+  return result;
+}
+
+static ComplexMatrix
+min (const ComplexMatrix& a, const ComplexMatrix& b)
+{
+  int nr = a.rows ();
+  int nc = a.columns ();
+  if (nr != b.rows () || nc != b.columns ())
+    {
+      error ("two-arg min expecting args of same size");
+      return ComplexMatrix ();
+    }
+
+  ComplexMatrix result (nr, nc);
+
+  for (int j = 0; j < nc; j++)
+    for (int i = 0; i < nr; i++)
+      {
+        double abs_a_elem = abs (a.elem (i, j));
+        double abs_b_elem = abs (b.elem (i, j));
+        if (abs_a_elem < abs_b_elem)
+          result.elem (i, j) = a.elem (i, j);
+        else
+          result.elem (i, j) = b.elem (i, j);
+      }
+
+  return result;
+}
+
+static Matrix
+max (const Matrix& a, const Matrix& b)
+{
+  int nr = a.rows ();
+  int nc = a.columns ();
+  if (nr != b.rows () || nc != b.columns ())
+    {
+      error ("two-arg max expecting args of same size");
+      return Matrix ();
+    }
+
+  Matrix result (nr, nc);
+
+  for (int j = 0; j < nc; j++)
+    for (int i = 0; i < nr; i++)
+      {
+	double a_elem = a.elem (i, j);
+	double b_elem = b.elem (i, j);
+	result.elem (i, j) = MAX (a_elem, b_elem);
+      }
+
+  return result;
+}
+
+static ComplexMatrix
+max (const ComplexMatrix& a, const ComplexMatrix& b)
+{
+  int nr = a.rows ();
+  int nc = a.columns ();
+  if (nr != b.rows () || nc != b.columns ())
+    {
+      error ("two-arg max expecting args of same size");
+      return ComplexMatrix ();
+    }
+
+  ComplexMatrix result (nr, nc);
+
+  for (int j = 0; j < nc; j++)
+    for (int i = 0; i < nr; i++)
+      {
+        double abs_a_elem = abs (a.elem (i, j));
+        double abs_b_elem = abs (b.elem (i, j));
+        if (abs_a_elem > abs_b_elem)
+          result.elem (i, j) = a.elem (i, j);
+        else
+          result.elem (i, j) = b.elem (i, j);
+      }
+
+  return result;
+}
+
+Octave_object
+column_min (const Octave_object& args, int nargout)
+{
+  Octave_object retval;
+
+  tree_constant arg1;
+  tree_constant arg2;
+  tree_constant_rep::constant_type arg1_type =
+    tree_constant_rep::unknown_constant;
+  tree_constant_rep::constant_type arg2_type =
+    tree_constant_rep::unknown_constant;
+
+  int nargin = args.length ();
+
+  switch (nargin)
+    {
+    case 3:
+      arg2 = args(2).make_numeric ();
+      arg2_type = arg2.const_type ();
+// Fall through...
+    case 2:
+      arg1 = args(1).make_numeric ();
+      arg1_type = arg1.const_type ();
+      break;
+    default:
+      panic_impossible ();
+      break;
+    }
+
+  if (nargin == 2 && (nargout == 1 || nargout == 0))
+    {
+      retval.resize (1);
+      switch (arg1_type)
+	{
+        case tree_constant_rep::scalar_constant:
+	  retval(0) = arg1.double_value ();
+          break;
+        case tree_constant_rep::complex_scalar_constant:
+          retval(0) = arg1.complex_value ();
+          break;
+        case tree_constant_rep::matrix_constant:
+          {
+  	    Matrix m = arg1.matrix_value ();
+	    if (m.rows () == 1)
+	      retval(0) = m.row_min ();
+	    else
+	      retval(0) = tree_constant (m.column_min (), 0);
+ 	  }
+          break;
+        case tree_constant_rep::complex_matrix_constant:
+          {
+            ComplexMatrix m = arg1.complex_matrix_value ();
+            if (m.rows () == 1)
+              retval(0) = m.row_min ();
+            else
+              retval(0) = tree_constant (m.column_min (), 0);
+          }
+	  break;
+	default:
+	  panic_impossible ();
+	  break;
+	}
+    }
+  else if (nargin == 2 && nargout == 2)
+    {
+      retval.resize (2);
+      switch (arg1_type)
+        {
+	case tree_constant_rep::scalar_constant:
+	  {
+	    retval(0) = arg1.double_value ();
+	    retval(1) = 1;
+	  }
+          break;
+	case tree_constant_rep::complex_scalar_constant:
+	  {
+	    retval(0) = arg1.complex_value ();
+	    retval(1) = 1;
+	  }
+          break;
+	case tree_constant_rep::matrix_constant:
+	  {
+	    Matrix m = arg1.matrix_value ();
+	    if (m.rows () == 1)
+	      {
+		retval(0) = m.row_min ();
+		retval(1) = m.row_min_loc ();
+	      }
+	    else
+	      {
+		retval(0) = tree_constant (m.column_min (), 0);
+		retval(1) = tree_constant (m.column_min_loc (), 0);
+	      }
+	  }
+          break;
+	case tree_constant_rep::complex_matrix_constant:
+	  {
+	    ComplexMatrix m = arg1.complex_matrix_value ();
+	    if (m.rows () == 1)
+	      {
+		retval(0) = m.row_min ();
+		retval(1) = m.row_min_loc ();
+	      }
+	    else
+	      {
+		retval(0) = tree_constant (m.column_min (), 0);
+		retval(1) = tree_constant (m.column_min_loc (), 0);
+	      }
+	  }
+          break;
+	default:
+	  panic_impossible ();
+	  break;
+        }
+    }
+  else if (nargin == 3)
+    {
+      if (arg1.rows () == arg2.rows ()
+	  && arg1.columns () == arg2.columns ())
+	{
+	  retval.resize (1);
+          switch (arg1_type)
+            {
+	    case tree_constant_rep::scalar_constant:
+	      {
+		double result;
+		double a_elem = arg1.double_value ();
+		double b_elem = arg2.double_value ();
+		result = MIN (a_elem, b_elem);
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::complex_scalar_constant:
+	      {
+		Complex result;
+		Complex a_elem = arg1.complex_value ();
+		Complex b_elem = arg2.complex_value ();
+		if (abs (a_elem) < abs (b_elem))
+		  result = a_elem;
+		else
+		  result = b_elem;
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::matrix_constant:
+	      {
+		Matrix result;
+		result = min (arg1.matrix_value (), arg2.matrix_value ());
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::complex_matrix_constant:
+	      {
+		ComplexMatrix result;
+		result = min (arg1.complex_matrix_value (),
+			      arg2.complex_matrix_value ());
+		retval(0) = result;
+	      }
+	      break;
+	    default:
+	      panic_impossible ();
+	      break;
+	    }
+	}
+      else
+	error ("min: nonconformant matrices");
+    }
+  else
+    panic_impossible ();
+
+  return retval;
+}
+
+Octave_object
+column_max (const Octave_object& args, int nargout)
+{
+  Octave_object retval;
+
+  tree_constant arg1;
+  tree_constant arg2;
+  tree_constant_rep::constant_type arg1_type =
+    tree_constant_rep::unknown_constant;
+  tree_constant_rep::constant_type arg2_type =
+    tree_constant_rep::unknown_constant;
+
+  int nargin = args.length ();
+
+  switch (nargin)
+    {
+    case 3:
+      arg2 = args(2).make_numeric ();
+      arg2_type = arg2.const_type ();
+// Fall through...
+    case 2:
+      arg1 = args(1).make_numeric ();
+      arg1_type = arg1.const_type ();
+      break;
+    default:
+      panic_impossible ();
+      break;
+    }
+
+  if (nargin == 2 && (nargout == 1 || nargout == 0))
+    {
+      retval.resize (1);
+      switch (arg1_type)
+	{
+        case tree_constant_rep::scalar_constant:
+	  retval(0) = arg1.double_value ();
+          break;
+        case tree_constant_rep::complex_scalar_constant:
+          retval(0) = arg1.complex_value ();
+          break;
+        case tree_constant_rep::matrix_constant:
+          {
+  	    Matrix m = arg1.matrix_value ();
+	    if (m.rows () == 1)
+	      retval(0) = m.row_max ();
+	    else
+	      retval(0) = tree_constant (m.column_max (), 0);
+ 	  }
+          break;
+        case tree_constant_rep::complex_matrix_constant:
+          {
+            ComplexMatrix m = arg1.complex_matrix_value ();
+            if (m.rows () == 1)
+              retval(0) = m.row_max ();
+            else
+              retval(0) = tree_constant (m.column_max (), 0);
+          }
+	  break;
+	default:
+	  panic_impossible ();
+	  break;
+	}
+    }
+  else if (nargin == 2 && nargout == 2)
+    {
+      retval.resize (2);
+      switch (arg1_type)
+        {
+	case tree_constant_rep::scalar_constant:
+	  {
+	    retval(0) = arg1.double_value ();
+	    retval(1) = 1;
+	  }
+          break;
+	case tree_constant_rep::complex_scalar_constant:
+	  {
+	    retval(0) = arg1.complex_value ();
+	    retval(1) = 1;
+	  }
+          break;
+	case tree_constant_rep::matrix_constant:
+	  {
+	    Matrix m = arg1.matrix_value ();
+	    if (m.rows () == 1)
+	      {
+		retval(0) = m.row_max ();
+		retval(1) = m.row_max_loc ();
+	      }
+	    else
+	      {
+		retval(0) = tree_constant (m.column_max (), 0);
+		retval(1) = tree_constant (m.column_max_loc (), 0);
+	      }
+	  }
+          break;
+	case tree_constant_rep::complex_matrix_constant:
+	  {
+	    ComplexMatrix m = arg1.complex_matrix_value ();
+	    if (m.rows () == 1)
+	      {
+		retval(0) = m.row_max ();
+		retval(1) = m.row_max_loc ();
+	      }
+	    else
+	      {
+		retval(0) = tree_constant (m.column_max (), 0);
+		retval(1) = tree_constant (m.column_max_loc (), 0);
+	      }
+	  }
+          break;
+	default:
+	  panic_impossible ();
+	  break;
+        }
+    }
+  else if (nargin == 3)
+    {
+      if (arg1.rows () == arg2.rows ()
+	  && arg1.columns () == arg2.columns ())
+	{
+	  retval.resize (1);
+          switch (arg1_type)
+            {
+	    case tree_constant_rep::scalar_constant:
+	      {
+		double result;
+		double a_elem = arg1.double_value ();
+		double b_elem = arg2.double_value ();
+		result = MAX (a_elem, b_elem);
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::complex_scalar_constant:
+	      {
+		Complex result;
+		Complex a_elem = arg1.complex_value ();
+		Complex b_elem = arg2.complex_value ();
+		if (abs (a_elem) > abs (b_elem))
+		  result = a_elem;
+		else
+		  result = b_elem;
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::matrix_constant:
+	      {
+		Matrix result;
+		result = max (arg1.matrix_value (), arg2.matrix_value ());
+		retval(0) = result;
+	      }
+              break;
+	    case tree_constant_rep::complex_matrix_constant:
+	      {
+		ComplexMatrix result;
+		result = max (arg1.complex_matrix_value (),
+			      arg2.complex_matrix_value ());
+		retval(0) = result;
+	      }
+	      break;
+	    default:
+	      panic_impossible ();
+	      break;
+	    }
+	}
+      else
+	error ("max: nonconformant matrices");
+    }
+  else
+    panic_impossible ();
+
+  return retval;
+}
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; page-delimiter: "^/\\*" ***
+;;; End: ***
+*/