fColVector.cc

Go to the documentation of this file.
00001 // ColumnVector manipulations.
00002 /*
00003 
00004 Copyright (C) 1994-2012 John W. Eaton
00005 Copyright (C) 2010 VZLU Prague
00006 
00007 This file is part of Octave.
00008 
00009 Octave is free software; you can redistribute it and/or modify it
00010 under the terms of the GNU General Public License as published by the
00011 Free Software Foundation; either version 3 of the License, or (at your
00012 option) any later version.
00013 
00014 Octave is distributed in the hope that it will be useful, but WITHOUT
00015 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
00016 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
00017 for more details.
00018 
00019 You should have received a copy of the GNU General Public License
00020 along with Octave; see the file COPYING.  If not, see
00021 <http://www.gnu.org/licenses/>.
00022 
00023 */
00024 
00025 #ifdef HAVE_CONFIG_H
00026 #include <config.h>
00027 #endif
00028 
00029 #include <iostream>
00030 
00031 #include "Array-util.h"
00032 #include "f77-fcn.h"
00033 #include "functor.h"
00034 #include "lo-error.h"
00035 #include "mx-base.h"
00036 #include "mx-inlines.cc"
00037 #include "oct-cmplx.h"
00038 
00039 // Fortran functions we call.
00040 
00041 extern "C"
00042 {
00043   F77_RET_T
00044   F77_FUNC (sgemv, SGEMV) (F77_CONST_CHAR_ARG_DECL,
00045                            const octave_idx_type&, const octave_idx_type&,
00046                            const float&, const float*, const octave_idx_type&,
00047                            const float*, const octave_idx_type&, const float&,
00048                            float*, const octave_idx_type&
00049                            F77_CHAR_ARG_LEN_DECL);
00050 }
00051 
00052 // Column Vector class.
00053 
00054 bool
00055 FloatColumnVector::operator == (const FloatColumnVector& a) const
00056 {
00057   octave_idx_type len = length ();
00058   if (len != a.length ())
00059     return 0;
00060   return mx_inline_equal (len, data (), a.data ());
00061 }
00062 
00063 bool
00064 FloatColumnVector::operator != (const FloatColumnVector& a) const
00065 {
00066   return !(*this == a);
00067 }
00068 
00069 FloatColumnVector&
00070 FloatColumnVector::insert (const FloatColumnVector& a, octave_idx_type r)
00071 {
00072   octave_idx_type a_len = a.length ();
00073 
00074   if (r < 0 || r + a_len > length ())
00075     {
00076       (*current_liboctave_error_handler) ("range error for insert");
00077       return *this;
00078     }
00079 
00080   if (a_len > 0)
00081     {
00082       make_unique ();
00083 
00084       for (octave_idx_type i = 0; i < a_len; i++)
00085         xelem (r+i) = a.elem (i);
00086     }
00087 
00088   return *this;
00089 }
00090 
00091 FloatColumnVector&
00092 FloatColumnVector::fill (float val)
00093 {
00094   octave_idx_type len = length ();
00095 
00096   if (len > 0)
00097     {
00098       make_unique ();
00099 
00100       for (octave_idx_type i = 0; i < len; i++)
00101         xelem (i) = val;
00102     }
00103 
00104   return *this;
00105 }
00106 
00107 FloatColumnVector&
00108 FloatColumnVector::fill (float val, octave_idx_type r1, octave_idx_type r2)
00109 {
00110   octave_idx_type len = length ();
00111 
00112   if (r1 < 0 || r2 < 0 || r1 >= len || r2 >= len)
00113     {
00114       (*current_liboctave_error_handler) ("range error for fill");
00115       return *this;
00116     }
00117 
00118   if (r1 > r2) { octave_idx_type tmp = r1; r1 = r2; r2 = tmp; }
00119 
00120   if (r2 >= r1)
00121     {
00122       make_unique ();
00123 
00124       for (octave_idx_type i = r1; i <= r2; i++)
00125         xelem (i) = val;
00126     }
00127 
00128   return *this;
00129 }
00130 
00131 FloatColumnVector
00132 FloatColumnVector::stack (const FloatColumnVector& a) const
00133 {
00134   octave_idx_type len = length ();
00135   octave_idx_type nr_insert = len;
00136   FloatColumnVector retval (len + a.length ());
00137   retval.insert (*this, 0);
00138   retval.insert (a, nr_insert);
00139   return retval;
00140 }
00141 
00142 FloatRowVector
00143 FloatColumnVector::transpose (void) const
00144 {
00145   return MArray<float>::transpose();
00146 }
00147 
00148 FloatColumnVector
00149 FloatColumnVector::abs (void) const
00150 {
00151   return do_mx_unary_map<float, float, std::abs> (*this);
00152 }
00153 
00154 FloatColumnVector
00155 real (const FloatComplexColumnVector& a)
00156 {
00157   return do_mx_unary_op<float, FloatComplex> (a, mx_inline_real);
00158 }
00159 
00160 FloatColumnVector
00161 imag (const FloatComplexColumnVector& a)
00162 {
00163   return do_mx_unary_op<float, FloatComplex> (a, mx_inline_imag);
00164 }
00165 
00166 // resize is the destructive equivalent for this one
00167 
00168 FloatColumnVector
00169 FloatColumnVector::extract (octave_idx_type r1, octave_idx_type r2) const
00170 {
00171   if (r1 > r2) { octave_idx_type tmp = r1; r1 = r2; r2 = tmp; }
00172 
00173   octave_idx_type new_r = r2 - r1 + 1;
00174 
00175   FloatColumnVector result (new_r);
00176 
00177   for (octave_idx_type i = 0; i < new_r; i++)
00178     result.xelem (i) = elem (r1+i);
00179 
00180   return result;
00181 }
00182 
00183 FloatColumnVector
00184 FloatColumnVector::extract_n (octave_idx_type r1, octave_idx_type n) const
00185 {
00186   FloatColumnVector result (n);
00187 
00188   for (octave_idx_type i = 0; i < n; i++)
00189     result.xelem (i) = elem (r1+i);
00190 
00191   return result;
00192 }
00193 
00194 // matrix by column vector -> column vector operations
00195 
00196 FloatColumnVector
00197 operator * (const FloatMatrix& m, const FloatColumnVector& a)
00198 {
00199   FloatColumnVector retval;
00200 
00201   octave_idx_type nr = m.rows ();
00202   octave_idx_type nc = m.cols ();
00203 
00204   octave_idx_type a_len = a.length ();
00205 
00206   if (nc != a_len)
00207     gripe_nonconformant ("operator *", nr, nc, a_len, 1);
00208   else
00209     {
00210       retval.clear (nr);
00211 
00212       if (nr != 0)
00213         {
00214           if (nc == 0)
00215             retval.fill (0.0);
00216           else
00217             {
00218               float *y = retval.fortran_vec ();
00219 
00220               F77_XFCN (sgemv, SGEMV, (F77_CONST_CHAR_ARG2 ("N", 1),
00221                                        nr, nc, 1.0f, m.data (), nr,
00222                                        a.data (), 1, 0.0f, y, 1
00223                                        F77_CHAR_ARG_LEN (1)));
00224             }
00225         }
00226     }
00227 
00228   return retval;
00229 }
00230 
00231 // diagonal matrix by column vector -> column vector operations
00232 
00233 FloatColumnVector
00234 operator * (const FloatDiagMatrix& m, const FloatColumnVector& a)
00235 {
00236   FloatColumnVector retval;
00237 
00238   octave_idx_type nr = m.rows ();
00239   octave_idx_type nc = m.cols ();
00240 
00241   octave_idx_type a_len = a.length ();
00242 
00243   if (nc != a_len)
00244     gripe_nonconformant ("operator *", nr, nc, a_len, 1);
00245   else
00246     {
00247       if (nr == 0 || nc == 0)
00248         retval.resize (nr, 0.0);
00249       else
00250         {
00251           retval.resize (nr);
00252 
00253           for (octave_idx_type i = 0; i < a_len; i++)
00254             retval.elem (i) = a.elem (i) * m.elem (i, i);
00255 
00256           for (octave_idx_type i = a_len; i < nr; i++)
00257             retval.elem (i) = 0.0;
00258         }
00259     }
00260 
00261   return retval;
00262 }
00263 
00264 // other operations
00265 
00266 float
00267 FloatColumnVector::min (void) const
00268 {
00269   octave_idx_type len = length ();
00270   if (len == 0)
00271     return 0.0;
00272 
00273   float res = elem (0);
00274 
00275   for (octave_idx_type i = 1; i < len; i++)
00276     if (elem (i) < res)
00277       res = elem (i);
00278 
00279   return res;
00280 }
00281 
00282 float
00283 FloatColumnVector::max (void) const
00284 {
00285   octave_idx_type len = length ();
00286   if (len == 0)
00287     return 0.0;
00288 
00289   float res = elem (0);
00290 
00291   for (octave_idx_type i = 1; i < len; i++)
00292     if (elem (i) > res)
00293       res = elem (i);
00294 
00295   return res;
00296 }
00297 
00298 std::ostream&
00299 operator << (std::ostream& os, const FloatColumnVector& a)
00300 {
00301 //  int field_width = os.precision () + 7;
00302   for (octave_idx_type i = 0; i < a.length (); i++)
00303     os << /* setw (field_width) << */ a.elem (i) << "\n";
00304   return os;
00305 }
00306 
00307 std::istream&
00308 operator >> (std::istream& is, FloatColumnVector& a)
00309 {
00310   octave_idx_type len = a.length();
00311 
00312   if (len > 0)
00313     {
00314       float tmp;
00315       for (octave_idx_type i = 0; i < len; i++)
00316         {
00317           is >> tmp;
00318           if (is)
00319             a.elem (i) = tmp;
00320           else
00321             break;
00322         }
00323     }
00324   return is;
00325 }
 All Classes Files Functions Variables Typedefs Enumerations Enumerator Friends Defines