base-lu.cc

Go to the documentation of this file.
00001 /*
00002 
00003 Copyright (C) 1996-2012 John W. Eaton
00004 Copyright (C) 2009 VZLU Prague
00005 
00006 This file is part of Octave.
00007 
00008 Octave is free software; you can redistribute it and/or modify it
00009 under the terms of the GNU General Public License as published by the
00010 Free Software Foundation; either version 3 of the License, or (at your
00011 option) any later version.
00012 
00013 Octave is distributed in the hope that it will be useful, but WITHOUT
00014 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
00015 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
00016 for more details.
00017 
00018 You should have received a copy of the GNU General Public License
00019 along with Octave; see the file COPYING.  If not, see
00020 <http://www.gnu.org/licenses/>.
00021 
00022 */
00023 
00024 #ifdef HAVE_CONFIG_H
00025 #include <config.h>
00026 #endif
00027 
00028 #include "base-lu.h"
00029 
00030 template <class lu_type>
00031 base_lu<lu_type>::base_lu (const lu_type& l, const lu_type& u,
00032                            const PermMatrix& p)
00033   : a_fact (u), l_fact (l), ipvt (p.pvec ())
00034 {
00035   if (l.columns () != u.rows ())
00036     (*current_liboctave_error_handler) ("lu: dimension mismatch");
00037 }
00038 
00039 template <class lu_type>
00040 bool
00041 base_lu <lu_type> :: packed (void) const
00042 {
00043   return l_fact.dims () == dim_vector ();
00044 }
00045 
00046 template <class lu_type>
00047 void
00048 base_lu <lu_type> :: unpack (void)
00049 {
00050   if (packed ())
00051     {
00052       l_fact = L ();
00053       a_fact = U (); // FIXME: sub-optimal
00054       ipvt = getp ();
00055     }
00056 }
00057 
00058 template <class lu_type>
00059 lu_type
00060 base_lu <lu_type> :: L (void) const
00061 {
00062   if (packed ())
00063     {
00064       octave_idx_type a_nr = a_fact.rows ();
00065       octave_idx_type a_nc = a_fact.cols ();
00066       octave_idx_type mn = (a_nr < a_nc ? a_nr : a_nc);
00067 
00068       lu_type l (a_nr, mn, lu_elt_type (0.0));
00069 
00070       for (octave_idx_type i = 0; i < a_nr; i++)
00071         {
00072           if (i < a_nc)
00073             l.xelem (i, i) = 1.0;
00074 
00075           for (octave_idx_type j = 0; j < (i < a_nc ? i : a_nc); j++)
00076             l.xelem (i, j) = a_fact.xelem (i, j);
00077         }
00078 
00079       return l;
00080     }
00081   else
00082     return l_fact;
00083 }
00084 
00085 template <class lu_type>
00086 lu_type
00087 base_lu <lu_type> :: U (void) const
00088 {
00089   if (packed ())
00090     {
00091       octave_idx_type a_nr = a_fact.rows ();
00092       octave_idx_type a_nc = a_fact.cols ();
00093       octave_idx_type mn = (a_nr < a_nc ? a_nr : a_nc);
00094 
00095       lu_type u (mn, a_nc, lu_elt_type (0.0));
00096 
00097       for (octave_idx_type i = 0; i < mn; i++)
00098         {
00099           for (octave_idx_type j = i; j < a_nc; j++)
00100             u.xelem (i, j) = a_fact.xelem (i, j);
00101         }
00102 
00103       return u;
00104     }
00105   else
00106     return a_fact;
00107 }
00108 
00109 template <class lu_type>
00110 lu_type
00111 base_lu <lu_type> :: Y (void) const
00112 {
00113   if (! packed ())
00114     (*current_liboctave_error_handler) ("lu: Y() not implemented for unpacked form");
00115   return a_fact;
00116 }
00117 
00118 template <class lu_type>
00119 Array<octave_idx_type>
00120 base_lu <lu_type> :: getp (void) const
00121 {
00122   if (packed ())
00123     {
00124       octave_idx_type a_nr = a_fact.rows ();
00125 
00126       Array<octave_idx_type> pvt (dim_vector (a_nr, 1));
00127 
00128       for (octave_idx_type i = 0; i < a_nr; i++)
00129         pvt.xelem (i) = i;
00130 
00131       for (octave_idx_type i = 0; i < ipvt.length(); i++)
00132         {
00133           octave_idx_type k = ipvt.xelem (i);
00134 
00135           if (k != i)
00136             {
00137               octave_idx_type tmp = pvt.xelem (k);
00138               pvt.xelem (k) = pvt.xelem (i);
00139               pvt.xelem (i) = tmp;
00140             }
00141         }
00142 
00143       return pvt;
00144     }
00145   else
00146     return ipvt;
00147 }
00148 
00149 template <class lu_type>
00150 PermMatrix
00151 base_lu <lu_type> :: P (void) const
00152 {
00153   return PermMatrix (getp (), false);
00154 }
00155 
00156 template <class lu_type>
00157 ColumnVector
00158 base_lu <lu_type> :: P_vec (void) const
00159 {
00160   octave_idx_type a_nr = a_fact.rows ();
00161 
00162   ColumnVector p (a_nr);
00163 
00164   Array<octave_idx_type> pvt = getp ();
00165 
00166   for (octave_idx_type i = 0; i < a_nr; i++)
00167     p.xelem (i) = static_cast<double> (pvt.xelem (i) + 1);
00168 
00169   return p;
00170 }
00171 
00172 template <class lu_type>
00173 bool
00174 base_lu<lu_type>::regular (void) const
00175 {
00176   bool retval = true;
00177 
00178   octave_idx_type k = std::min (a_fact.rows (), a_fact.columns ());
00179 
00180   for (octave_idx_type i = 0; i < k; i++)
00181     {
00182       if (a_fact(i, i) == lu_elt_type ())
00183         {
00184           retval = false;
00185           break;
00186         }
00187     }
00188 
00189   return retval;
00190 }
 All Classes Files Functions Variables Typedefs Enumerations Enumerator Friends Defines