AbstractLinAlgPack: C++ Interfaces For Vectors, Matrices And Related Linear Algebra Objects Version of the Day
AbstractLinAlgPack_MA28_CppDecl.hpp
00001 // @HEADER
00002 // ***********************************************************************
00003 // 
00004 // Moocho: Multi-functional Object-Oriented arCHitecture for Optimization
00005 //                  Copyright (2003) Sandia Corporation
00006 // 
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
00009 // 
00010 // This library is free software; you can redistribute it and/or modify
00011 // it under the terms of the GNU Lesser General Public License as
00012 // published by the Free Software Foundation; either version 2.1 of the
00013 // License, or (at your option) any later version.
00014 //  
00015 // This library is distributed in the hope that it will be useful, but
00016 // WITHOUT ANY WARRANTY; without even the implied warranty of
00017 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00018 // Lesser General Public License for more details.
00019 //  
00020 // You should have received a copy of the GNU Lesser General Public
00021 // License along with this library; if not, write to the Free Software
00022 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
00023 // USA
00024 // Questions? Contact Roscoe A. Bartlett (rabartl@sandia.gov) 
00025 // 
00026 // ***********************************************************************
00027 // @HEADER
00028 //
00029 // C declarations for MA28 functions.  These declarations should not have to change
00030 // for different platforms.  As long as the fortran object code uses capitalized
00031 // names for its identifers then the declarations in Teuchos_F77_wrappers.h should be
00032 // sufficent for portability.
00033 
00034 #ifndef MA28_CPPDECL_H
00035 #define MA28_CPPDECL_H
00036 
00037 #include "Teuchos_F77_wrappers.h"
00038 
00039 namespace MA28_CppDecl {
00040 
00041 // Declarations that will link to the fortran object file.
00042 // These may change for different platforms
00043 
00044 using FortranTypes::f_int;      // INTEGER
00045 using FortranTypes::f_real;     // REAL
00046 using FortranTypes::f_dbl_prec;   // DOUBLE PRECISION
00047 using FortranTypes::f_logical;    // LOGICAL
00048 
00049 namespace Fortran {
00050 extern "C" {
00051 
00052 // analyze and factorize a matrix
00053 FORTRAN_FUNC_DECL_UL(void,MA28AD,ma28ad) (const f_int& n, const f_int& nz, f_dbl_prec a[], const f_int& licn
00054   , f_int irn[], const f_int& lirn, f_int icn[], const f_dbl_prec& u, f_int ikeep[], f_int iw[]
00055   , f_dbl_prec w[], f_int* iflag);
00056   
00057 // factor using previous analyze
00058 FORTRAN_FUNC_DECL_UL(void,MA28BD,ma28bd) (const f_int& n, const f_int& nz, f_dbl_prec a[], const f_int& licn
00059   , const f_int ivect[], const f_int jvect[], const f_int icn[], const f_int ikeep[], f_int iw[]
00060   , f_dbl_prec w[], f_int* iflag);
00061 
00062 // solve for rhs using internally stored factorized matrix
00063 FORTRAN_FUNC_DECL_UL(void,MA28CD,ma28cd) (const f_int& n, const f_dbl_prec a[], const f_int& licn, const f_int icn[]
00064   , const f_int ikeep[], f_dbl_prec rhs[], f_dbl_prec w[], const f_int& mtype);
00065 
00066 // /////////////////////////////////////////////////////////////////////////////////////////
00067 // Declare structs that represent the MA28 common blocks.  
00068 // These are the common block variables that are ment to be accessed by the user
00069 // Some are used to set the options of MA28 and others return information
00070 // about the attempts to solve the system.
00071 // I want to provide the access functions that allow all of those common block
00072 // variables that are ment to be accessed by the user to be accessable.
00073 // For each of the common data items there will be a get operation that 
00074 // returns the variable value.  For those items that are ment to be
00075 // set by the user there will also be set operations.
00076 
00077 //  COMMON /MA28ED/ LP, MP, LBLOCK, GROW
00078 //  INTEGER LP, MP
00079 //  LOGICAL LBLOCK, GROW
00080 struct MA28ED_struct {
00081   f_int   lp;
00082   f_int   mp;
00083   f_logical lblock;
00084   f_logical grow;
00085 };
00086 extern MA28ED_struct FORTRAN_NAME_UL(MA28ED,ma28ed); // link to fortan common block
00087 
00088 //  COMMON /MA28FD/ EPS, RMIN, RESID, IRNCP, ICNCP, MINIRN, MINICN,
00089 // * IRANK, ABORT1, ABORT2
00090 //  INTEGER IRNCP, ICNCP, MINIRN, MINICN, IRANK
00091 //  LOGICAL ABORT1, ABORT2
00092 //  REAL EPS, RMIN, RESID
00093 struct MA28FD_struct {
00094   f_dbl_prec  eps;
00095   f_dbl_prec  rmin;
00096   f_dbl_prec  resid;
00097   f_int   irncp;
00098   f_int   icncp;
00099   f_int   minirn;
00100   f_int   minicn;
00101   f_int   irank;
00102   f_logical abort1;
00103   f_logical abort2;
00104 };
00105 extern MA28FD_struct FORTRAN_NAME_UL(MA28FD,ma28fd); // link to fortan common block
00106 
00107 
00108 //  COMMON /MA28GD/ IDISP
00109 //  INTEGER IDISP
00110 struct MA28GD_struct {
00111   f_int   idisp[2];
00112 };
00113 extern MA28GD_struct FORTRAN_NAME_UL(MA28GD,ma28gd); // link to fortan common block
00114 
00115 //  COMMON /MA28HD/ TOL, THEMAX, BIG, DXMAX, ERRMAX, DRES, CGCE,
00116 // * NDROP, MAXIT, NOITER, NSRCH, ISTART, LBIG
00117 //  INTEGER NDROP, MAXIT, NOITER, NSRCH, ISTART
00118 //  LOGICAL LBIG
00119 //  REAL TOL, THEMAX, BIG, DXMAX, ERRMAX, DRES, CGCE
00120 struct MA28HD_struct {
00121   f_dbl_prec  tol;
00122   f_dbl_prec  themax;
00123   f_dbl_prec  big;
00124   f_dbl_prec  dxmax;
00125   f_dbl_prec  errmax;
00126   f_dbl_prec  dres;
00127   f_dbl_prec  cgce;
00128   f_int   ndrop;
00129   f_int   maxit;
00130   f_int   noiter;
00131   f_int   nsrch;
00132   f_int   istart;
00133   f_logical lbig;
00134 };
00135 extern MA28HD_struct FORTRAN_NAME_UL(MA28HD,ma28hd); // link to fortan common block
00136 
00137 //  COMMON /MA30ED/ LP, ABORT1, ABORT2, ABORT3
00138 //  INTEGER LP
00139 //  LOGICAL ABORT1, ABORT2, ABORT3
00140 struct MA30ED_struct {
00141   f_int   lp;
00142   f_logical abort1;
00143   f_logical abort2;
00144   f_logical abort3;
00145 };
00146 extern MA30ED_struct FORTRAN_NAME_UL(MA30ED,ma30ed); // link to fortan common block
00147 
00148 //  COMMON /MA30FD/ IRNCP, ICNCP, IRANK, IRN, ICN
00149 //  INTEGER IRNCP, ICNCP, IRANK, IRN, ICN
00150 struct MA30FD_struct {
00151   f_int   irncp;
00152   f_int   icncp;
00153   f_int   irank;
00154   f_int   minirn;
00155   f_int   minicn;
00156 };
00157 extern MA30FD_struct FORTRAN_NAME_UL(MA30FD,ma30fd); // link to fortan common block
00158 
00159 //  COMMON /MA30GD/ EPS, RMIN
00160 //  DOUBLE PRECISION EPS, RMIN
00161 struct MA30GD_struct {
00162   f_dbl_prec  eps;
00163   f_dbl_prec  rmin;
00164 };
00165 extern MA30GD_struct FORTRAN_NAME_UL(MA30GD,ma30gd); // link to fortan common block
00166 
00167 //  COMMON /MA30HD/ RESID
00168 //  DOUBLE PRECISION RESID
00169 struct MA30HD_struct {
00170   f_dbl_prec  resid;
00171 };
00172 extern MA30HD_struct FORTRAN_NAME_UL(MA30HD,ma30hd); // link to fortan common block
00173 
00174 //  COMMON /MA30ID/ TOL, BIG, NDROP, NSRCH, LBIG
00175 //  INTEGER NDROP, NSRCH
00176 //  LOGICAL LBIG
00177 //  DOUBLE PRECISION TOL, BIG
00178 struct MA30ID_struct {
00179   f_dbl_prec  tol;
00180   f_dbl_prec  big;
00181   f_int   ndrop;
00182   f_int   nsrch;
00183   f_logical lbig;
00184 };
00185 extern MA30ID_struct FORTRAN_NAME_UL(MA30ID,ma30id); // link to fortan common block
00186 
00187 //  COMMON /MC23BD/ LP,NUMNZ,NUM,LARGE,ABORT
00188 //  INTEGER LP, NUMNZ, NUM, LARGE
00189 //  LOGICAL ABORT
00190 struct MC23BD_struct {
00191   f_int   lp;
00192   f_int   numnz;
00193   f_int   num;
00194   f_int   large;
00195   f_logical abort;
00196 };
00197 extern MC23BD_struct FORTRAN_NAME_UL(MC23BD,mc23bd); // link to fortan common block
00198 
00199 
00200 } // end extern "C"
00201 } // end namespace Fortran
00202 
00203 
00204 /* * @name {\bf MA28 C++ Declarations}.
00205   *
00206   * These the C++ declarations for MA28 functions and common block data.
00207   * These declarations will not change for different platforms.
00208   * All of these functions are in the C++ namespace #MA28_CppDecl#.
00209   *
00210   * These functions perform the three phases that are normally associated
00211   * with solving sparse systems of linear equations; analyze (and factorize)
00212   * , factorize, and solve.  The MA28 interface uses a coordinate format
00213   * (aij, i, j) for the sparse matrix.
00214   * 
00215   * There are three interface routienes that perform these steps:
00216   * \begin{description}
00217   * \item[#ma28ad#] Analyzes and factorizes a sparse matrix stored in #a#, #irn#
00218   *   , #icn# and returns the factorized matrix data structures in #a#, #icn#
00219   *   , and #ikeep#.
00220   * \item[#ma28bd#] Factorizes a matrix with the same sparsity structure that was
00221   *   previously factorized by #ma28ad#.  Information about the row and column
00222   *   permutations, fill-in elements etc. from the previous analyze and factorization
00223   *   is passed in the arguments #icn#, and #ikeep#.  The matrix to be
00224   *   factorized is passed in #a#, #ivect#, and #jvect# and the non-zero
00225   *   elements of the factorization are returned in #a#.
00226   * \item[#ma28cd#] Solves for a dense right hand side (rhs) given a matrix factorized
00227   *   by #ma28ad# or #ma28bd#.  The rhs is passed in #rhs# and the solution
00228   *   is returned in #rhs#.  The factorized matrix is passed in by #a#, #icn#
00229   *   and #ikeep#.  The transposed or the non-transposed system can be solved
00230   *   for by passing in #mtype != 1# and #mtype == 1# respectively.
00231   */
00232 
00233 // @{
00234 //    begin MA28 C++ Declarations
00235 
00236 /* * @name {\bf MA28 / MA30 Common Block Access}.
00237   *
00238   * These are references to structures that allow C++ users to set and retrive
00239   * values of the MA28xD and MA30xD common blocks.   Some of the common block
00240   * items listed below for MA28xD are also present in MA30xD.  The control
00241   * parameters (abort1, eps, etc.) for MA28xD are transfered to the equivalent
00242   * common block variables in the #ma28ad# function but not in any of the other
00243   * functions.
00244   *
00245   * The internal states for MA28, MA30, and MC23 are determined by the 
00246   * values in these common block variables as there are no #SAVE# variables
00247   * in any of the functions.  So to use MA28 with more than
00248   * one sparse matrix at a time you just have to keep copies of these
00249   * common block variable for each system and then set them when every
00250   * you want to work with that system agian.  This is very good news.
00251   *
00252   * These common block variables are:
00253   * \begin{description}
00254   * \item[lp, mp]
00255   *   Integer: Used by the subroutine as the unit numbers for its warning
00256   *   and diagnostic messages. Default value for both is 6 (for line
00257   *   printer output). the user can either reset them to a different
00258   *   stream number or suppress the output by setting them to zero.
00259   *   While #lp# directs the output of error diagnostics from the
00260   *   principal subroutines and internally called subroutines, #mp#
00261   *   controls only the output of a message which warns the user that he
00262   *   has input two or more non-zeros a(i), . . ,a(k) with the same row
00263   *   and column indices.  The action taken in this case is to proceed
00264   *   using a numerical value of a(i)+...+a(k). in the absence of other
00265   *   errors, #iflag# will equal -14 on exit.
00266   * \item[lblock]
00267   *   Logical: Controls an option of first
00268   *   preordering the matrix to block lower triangular form (using
00269   *   harwell subroutine mc23a). The preordering is performed if #lblock#
00270   *   is equal to its default value of #true# if #lblock# is set to
00271   *   #false# , the option is not invoked and the space allocated to
00272   *   #ikeep# can be reduced to 4*n+1.
00273   * \item[grow]
00274   *    Logical: If it is left at its default value of
00275   *   #true# , then on return from ma28a/ad or ma28b/bd, w(1) will give
00276   *   an estimate (an upper bound) of the increase in size of elements
00277   *   encountered during the decomposition. If the matrix is well
00278   *   scaled, then a high value for w(1), relative to the largest entry
00279   *   in the input matrix, indicates that the LU decomposition may be
00280   *   inaccurate and the user should be wary of his results and perhaps
00281   *   increase u for subsequent runs.  We would like to emphasise that
00282   *   this value only relates to the accuracy of our LU decomposition
00283   *   and gives no indication as to the singularity of the matrix or the
00284   *   accuracy of the solution.  This upper bound can be a significant
00285   *   overestimate particularly if the matrix is badly scaled. If an
00286   *   accurate value for the growth is required, #lbig# (q.v.) should be
00287   *   set to #true#
00288   * \item[eps, rmin]
00289   *   Double Precision:  If on entry to ma28b/bd, #eps# is less
00290   *   than one, then #rmin# will give the smallest ratio of the pivot to
00291   *   the largest element in the corresponding row of the upper
00292   *   triangular factor thus monitoring the stability of successive
00293   *   factorizations. if rmin becomes very large and w(1) from
00294   *   ma28b/bd is also very large, it may be advisable to perform a
00295   *    new decomposition using ma28a/ad.
00296   * \item[resid]
00297   *   Double Precision:  On exit from ma28c/cd gives the value
00298   *   of the maximum residual over all the equations unsatisfied because
00299   *   of dependency (zero pivots).
00300   * \item[irncp,icncp]
00301   *   Integer:  Monitors the adequacy of "elbow
00302   *   room" in #irn# and #a#/#icn# respectively. If either is quite large (say
00303   *   greater than n/10), it will probably pay to increase the size of
00304   *   the corresponding array for subsequent runs. if either is very low
00305   *   or zero then one can perhaps save storage by reducing the size of
00306   *   the corresponding array.
00307   * \item[minirn, minicn]
00308   *   Integer: In the event of a
00309   *   successful return (#iflag# >= 0 or #iflag# = -14) give the minimum size
00310   *   of #irn# and #a#/#icn# respectively which would enable a successful run
00311   *   on an identical matrix. On an exit with #iflag# equal to -5, #minicn#
00312   *   gives the minimum value of #icn# for success on subsequent runs on
00313   *   an identical matrix. in the event of failure with #iflag# = -6, -4,
00314   *   -3, -2, or -1, then #minicn# and #minirn# give the minimum value of
00315   *   #licn# and #lirn# respectively which would be required for a
00316   *   successful decomposition up to the point at which the failure
00317   *   occurred.
00318   * \item[irank]
00319   *   Integer:  Gives an upper bound on the rank of the matrix.
00320   * \item[abort1]
00321   *   Logical:  Default value #true#.  If #abort1# is
00322   *   set to #false# then ma28a/ad will decompose structurally singular
00323   *   matrices (including rectangular ones).
00324   * \item[abort2]
00325   *   Logical:   Default value #true#.  If #abort2# is
00326   *   set to #false# then ma28a/ad will decompose numerically singular
00327   *   matrices.
00328   * \item[idisp]
00329   *   Integer[2]:  On output from ma28a/ad, the
00330   *   indices of the diagonal blocks of the factors lie in positions
00331   *   idisp(1) to idisp(2) of #a#/#icn#. This array must be preserved
00332   *   between a call to ma28a/ad and subsequent calls to ma28b/bd,
00333   *   ma28c/cd or ma28i/id.
00334   * \item[tol]
00335   *   Double Precision:  If it is set to a positive value, then any
00336   *   non-zero whose modulus is less than #tol# will be dropped from the
00337   *   factorization.  The factorization will then require less storage
00338   *   but will be inaccurate.  After a run of ma28a/ad with #tol# positive
00339   *   it is not possible to use ma28b/bd and the user is recommended to
00340   *   use ma28i/id to obtain the solution.  The default value for #tol# is
00341   *   0.0.
00342   * \item[themax]
00343   *   Double Precision:  On exit from ma28a/ad, it will hold the
00344   *   largest entry of the original matrix.
00345   * \item[big]
00346   *   Double Precision:  If #lbig# has been set to #true#, #big# will hold
00347   *   the largest entry encountered during the factorization by ma28a/ad
00348   *   or ma28b/bd.
00349   * \item[dxmax]
00350   *   Double Precision:  On exit from ma28i/id, #dxmax# will be set to
00351   *   the largest component of the solution.
00352   * \item[errmax]
00353   *   Double Precision:  On exit from ma28i/id, If #maxit# is
00354   *   positive, #errmax# will be set to the largest component in the
00355   *   estimate of the error.
00356   * \item[dres]
00357   *   Double Precision:  On exit from ma28i/id, if #maxit# is positive,
00358   *   #dres# will be set to the largest component of the residual.
00359   * \item[cgce]
00360   *   Double Precision:  It is used by ma28i/id to check the
00361   *   convergence rate.  if the ratio of successive corrections is
00362   *   not less than #cgce# then we terminate since the convergence
00363   *   rate is adjudged too slow.
00364   * \item[ndrop]
00365   *   Integer:  If #tol# has been set positive, on exit
00366   *   from ma28a/ad, #ndrop# will hold the number of entries dropped from
00367   *   the data structure.
00368   * \item[maxit]
00369   *   Integer:  It is the maximum number of iterations
00370   *   performed by ma28i/id. It has a default value of 16.
00371   * \item[noiter]
00372   *   Integer:  It is set by ma28i/id to the number of
00373   *   iterative refinement iterations actually used.
00374   * \item[nsrch]
00375   *   Integer:  If #nsrch# is set to a value less than #n#,
00376   *   then a different pivot option will be employed by ma28a/ad.  This
00377   *   may result in different fill-in and execution time for ma28a/ad.
00378   *   If #nsrch# is less than or equal to #n#, the workspace array #iw# can be
00379   *   reduced in length.  The default value for nsrch is 32768.
00380   * \item[istart]
00381   *   Integer:  If #istart# is set to a value other than
00382   *   zero, then the user must supply an estimate of the solution to
00383   *   ma28i/id.  The default value for istart is zero.
00384   * \item[lbig]
00385   *   Logical:  If #lbig# is set to #true#, the value of the
00386   *   largest element encountered in the factorization by ma28a/ad or
00387   *   ma28b/bd is returned in #big#.  setting #lbig# to #true#  will
00388   *   increase the time for ma28a/ad marginally and that for ma28b/bd
00389   *   by about 20%.  The default value for #lbig# is #false#.
00390   */
00391 
00392 // @{
00393 //    begin MA28 Common Block Access
00394 
00395 // / Common block with members: #lp#, #mp#, #lblock#, #grow#
00396 static MA28ED_struct &ma28ed_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA28ED,ma28ed);
00397 // / Common block with members: #eps#, #rmin#, #resid#, #irncp#, #icncp#, #minirc#, #minicn#, #irank#, #abort1#, #abort2#
00398 static MA28FD_struct &ma28fd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA28FD,ma28fd);
00399 // / Common block with members: #idisp#
00400 static MA28GD_struct &ma28gd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA28GD,ma28gd);
00401 // / Common block with members: #tol#, #themax#, #big#, #bxmax#, #errmax#, #dres#, #cgce#, #ndrop#, #maxit#, #noiter#, #nsrch#, #istart#, #lbig#
00402 static MA28HD_struct &ma28hd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA28HD,ma28hd);
00403 // / Common block with members: #lp#, #abort1#, #abort2#, #abort3#
00404 static MA30ED_struct &ma30ed_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA30ED,ma30ed);
00405 // / Common block with members: #irncp#, #icncp#, #irank#, #irn#, #icn#
00406 static MA30FD_struct &ma30fd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA30FD,ma30fd);
00407 // / Common block with members: #eps#, #rmin#
00408 static MA30GD_struct &ma30gd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA30GD,ma30gd);
00409 // / Common block with members: #resid#
00410 static MA30HD_struct &ma30hd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA30HD,ma30hd);
00411 // / Common block with members: #tol#, #big#, #ndrop#, #nsrch#, #lbig#
00412 static MA30ID_struct &ma30id_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MA30ID,ma30id);
00413 // / Common block with members: #lp#, #numnz#, #num#, #large#, #abort#
00414 static MC23BD_struct &mc23bd_cb = FORTRAN_COMMMON_BLOCK_NAME_UL(MC23BD,mc23bd);
00415 
00416   // The reason that these are declared static is because I need to
00417   // make sure that these references are initialized before they are
00418   // used in other global defintions.  This means that every translation
00419   // unit will have their own copy of this data.  To reduce this code
00420   // blot you could declair them as pointers then set then using the 
00421   // trick of an initialization class (Myers).
00422 
00423 //    end MA28 Common Block Access
00424 // @}
00425 
00426 // /
00427 /* * Analyze and factor a sparse matrix.
00428   *
00429   * This function analyzes (determines row and column pivots to minimize
00430   * fill-in and result in a better conditioned factorization) then factors
00431   * (calculates upper and lower triangular factors for the determined
00432   * row and column pivots) the permuted system.  The function takes a sparse
00433   * matrix stored in coordinate form ([Aij, i, j] => [#a#, #irn#, #icn#]) and
00434   * factorizes it.  On entry, the first #nz# elements of #a#, #irn#, and
00435   * #icn# hold the matrix elements.  The remaining entires of #a#, #irn#
00436   * , and #icn# hold the fill-in entries after the matrix factorization is
00437   * complete.
00438   *
00439   * The amount of fill-in is influenced by #u#.  A value of #u = 1.0# gives partial
00440   * pivoting where fill-in is sacrificed for the sake of numerical stability and
00441   * #u = 0.0# gives pivoting that strictly minimizes fill-in.
00442   *
00443   * The parameters #ikeep#, #iw#, and #w# are used as workspace but
00444   * #ikeep# contains important information about the factoriation
00445   * on return.
00446   *
00447   * The parameter #iflag# is used return error information about the attempt
00448   * to factorized the system.
00449   *
00450   * @param  n [input] Order of the system being solved.
00451   * @param  nz  [input] Number of non-zeros of the input matrix (#nz >= n#).
00452   *       The ratio #nz/(n*n)# equals the sparsity fraction for the matrix.
00453   * @param  a [input/output] Length = #licn#.  The first #nz# entries hold the
00454   *       non-zero entries of the input matrix on input and
00455   *       the non-zero entries of the factorized matrix on exit.
00456   * @param  licn  [input] length of arrays #a# and #icn#.  This
00457   *         is the total amount of storage advalable for the
00458   *         non-zero entries of the factorization of #a#.
00459   *         therefore #licn# must be greater than #nz#. How
00460   *         much greater depends on the amount of fill-in.
00461   * @param  irn [input/modifed] Length = #ircn#.  The first #nz# entries hold
00462   *       the row indices of the matrix #a# on input.
00463   * @param  ircn  [input] Lenght of irn.
00464   * @param  icn [input/output] Length = #licn#.  Holds column indices of #a# on 
00465   *       entry and the column indices of the reordered
00466   *       #a# on exit.
00467   * @param  u [input] Controls partial pivoting.
00468   *       \begin{description}
00469   *       \item[#* u >= 1.0#]
00470   *         Uses partial pivoting for maximum numerical stability
00471   *         at the expense of some extra fill-in.
00472   *       \item[#* 1.0 < u < 0.0#]
00473   *         Balances numerical stability and fill-in with #u# near 1.0
00474   *         favoring stability and #u# near 0.0 favoring less fill-in.
00475   *       \item[#* u <= 0.0#]
00476   *         Determines row and column pivots to minimize fill-in
00477   *         irrespective of the numerical stability of the 
00478   *         resulting factorization.
00479   *       \end{description}
00480   * @param  ikeep [output] Length = 5 * #n#.  On exist contains information about 
00481   *         the factorization.
00482   *         \begin{description}
00483   *         \item[#* #ikeep(:,1)]
00484   *           Holds the total length of the part of row i in
00485   *           the diagonal block.
00486   *         \item[#* #ikeep(:,2)]
00487   *           Holds the row pivots.  Row #ikeep(i,2)# of the
00488   *           input matrix is the ith row of the pivoted matrix
00489   *           which is factorized.
00490   *         \item[#* #ikeep(:,3)]
00491   *           Holds the column pivots.  Column #ikeep(i,3)# of the
00492   *           input matrix is the ith column of the pivoted matrix
00493   *           which is factorized.
00494   *         \item[#* #ikeep(:,4)]
00495   *           Holds the length of the part of row i in the L
00496   *           part of the L/U decomposition.
00497   *         \item[#* #ikeep(:,5)]
00498   *           Holds the length of the part of row i in the
00499   *           off-diagonal blocks.  If there is only one
00500   *           diagonal block, #ikeep(i,5)# is set to -1.
00501   *         \end{description}
00502   * @param  iw  [] Length = #8*n#.  Integer workspace.
00503   * @param  w [] Length = #n#.  Real workspace.
00504   * @param  iflag [output] Used to return error condtions.
00505   *         \begin{description}
00506   *         \item[#* >= 0#] Success.
00507   *         \item[#* < 0#] Some error has occured.
00508   *         \end{description}
00509   */
00510 inline void ma28ad(const f_int& n, const f_int& nz, f_dbl_prec a[], const f_int& licn
00511   , f_int irn[], const f_int& lirn, f_int icn[], const f_dbl_prec& u, f_int ikeep[], f_int iw[]
00512   , f_dbl_prec w[], f_int* iflag)
00513 { Fortran::FORTRAN_FUNC_CALL_UL(MA28AD,ma28ad) (n,nz,a,licn,irn,lirn,icn,u,ikeep,iw,w,iflag); }
00514 
00515 // /
00516 /* * Factor a sparse matrix using previous analyze pivots.
00517   *
00518   * This function uses the pivots determined from a previous factorization
00519   * to factorize the matrix #a# again.  The assumption is that the 
00520   * sparsity structure of #a# has not changed but only its numerical 
00521   * values.  It is therefore possible that the refactorization may 
00522   * become unstable.
00523   *
00524   * The matrix to be refactorized on order #n# with #nz# non-zero elements
00525   * is input in coordinate format in #a#, #ivect# and #jvect#. 
00526   *
00527   * Information about the factorization is contained in the #icn# and
00528   * #ikeep# arrays returned from \Ref{ma28ad}.
00529   *
00530   * @param  n [input] Order of the system being solved.
00531   * @param  nz  [input] Number of non-zeros of the input matrix
00532   * @param  a [input/output] Length = #licn#.  The first #nz# entries hold the
00533   *       non-zero entries of the input matrix on input and
00534   *       the non-zero entries of the factorized matrix on exit.
00535   * @param  licn  [input] length of arrays #a# and #icn#.  This
00536   *         is the total amount of storage avalable for the
00537   *         non-zero entries of the factorization of #a#.
00538   *         therefore #licn# must be greater than #nz#. How
00539   *         much greater depends on the amount of fill-in.
00540   * @param  icn [input] Length = #licn#.  Same array output from #ma28ad#.
00541   *       It contains information about the analyze step.
00542   * @param  ikeep [input] Length = 5 * #n#.  Same array output form #ma28ad#.
00543   *         It contains information about the analyze step.
00544   * @param  iw  [] Length = #8*n#.  Integer workspace.
00545   * @param  w [] Length = #n#.  Real workspace.
00546   * @param  iflag [output] Used to return error condtions.
00547   *         \begin{description}
00548   *         \item[#* >= 0#] Success
00549   *         \item[#* < 0#] Some error has occured.
00550   *         \end{description}
00551   */
00552 inline void ma28bd(const f_int& n, const f_int& nz, f_dbl_prec a[], const f_int& licn
00553   , const f_int ivect[], const f_int jvect[], const f_int icn[], const f_int ikeep[], f_int iw[]
00554   , f_dbl_prec w[], f_int* iflag)
00555 { Fortran::FORTRAN_FUNC_CALL_UL(MA28BD,ma28bd) (n,nz,a,licn,ivect,jvect,icn,ikeep,iw,w,iflag);  }
00556 
00557 // /
00558 /* * Solve for a rhs using a factorized matrix.
00559   *
00560   * This function solves for a rhs given a matrix factorized by
00561   * #ma28ad# or #ma28bd#.  The right hand side (rhs) is passed
00562   * in in #rhs# and the solution is return in #rhs#.  The 
00563   * factorized matrix is passed in in #a#, #icn#, and #ikeep#
00564   * which were set by #ma28ad# and/or #ma28bd#. The 
00565   *
00566   * The matrix or its transpose can be solved for by selecting
00567   * #mtype == 1# or #mtype != 1# respectively.
00568   *
00569   * @param  n [input] Order of the system being solved.
00570   * @param  a [input] Length = #licn#.  Contains the non-zero
00571   *       elements of the factorized matrix.
00572   * @param  licn  [input] length of arrays #a# and #icn#.  This
00573   *         is the total amount of storage avalable for the
00574   *         non-zero entries of the factorization of #a#.
00575   *         therefore #licn# must be greater than #nz#. How
00576   *         much greater depends on the amount of fill-in.
00577   * @param  icn [input] Length = #licn#.  Same array output from #ma28ad#.
00578   *       It contains information about the analyze step.
00579   * @param  ikeep [input] Length = 5 * #n#.  Same array output form #ma28ad#.
00580   *         It contains information about the analyze step.
00581   * @param  w [] Length = #n#.  Real workspace.
00582   * @param  mtype [input] Instructs to solve using the matrix or its transpoze.
00583   *         \begin{description}
00584   *         \item[#* mtype == 1#] Solve using the non-transposed matrix.
00585   *         \item[#* mtype != 1#] Solve using the transposed matrix.
00586   *         \end{description} 
00587   */
00588 inline void ma28cd(const f_int& n, const f_dbl_prec a[], const f_int& licn, const f_int icn[]
00589   , const f_int ikeep[], f_dbl_prec rhs[], f_dbl_prec w[], const f_int& mtype)
00590 { Fortran::FORTRAN_FUNC_CALL_UL(MA28CD,ma28cd) (n,a,licn,icn,ikeep,rhs,w,mtype);  }
00591 
00592 //    end MA28 C++ Declarations
00593 // @}
00594 
00595 } // end namespace MA28_CDecl
00596 
00597 #endif // MA28_CPPDECL_H
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends