1    	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2    	/*                                                                           */
3    	/*                  This file is part of the class library                   */
4    	/*       SoPlex --- the Sequential object-oriented simPlex.                  */
5    	/*                                                                           */
6    	/*  Copyright (c) 1996-2023 Zuse Institute Berlin (ZIB)                      */
7    	/*                                                                           */
8    	/*  Licensed under the Apache License, Version 2.0 (the "License");          */
9    	/*  you may not use this file except in compliance with the License.         */
10   	/*  You may obtain a copy of the License at                                  */
11   	/*                                                                           */
12   	/*      http://www.apache.org/licenses/LICENSE-2.0                           */
13   	/*                                                                           */
14   	/*  Unless required by applicable law or agreed to in writing, software      */
15   	/*  distributed under the License is distributed on an "AS IS" BASIS,        */
16   	/*  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */
17   	/*  See the License for the specific language governing permissions and      */
18   	/*  limitations under the License.                                           */
19   	/*                                                                           */
20   	/*  You should have received a copy of the Apache-2.0 license                */
21   	/*  along with SoPlex; see the file LICENSE. If not email to soplex@zib.de.  */
22   	/*                                                                           */
23   	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
24   	
25   	/**@file  slinsolver.h
26   	 * @brief Sparse Linear Solver virtual base class.
27   	 */
28   	#ifndef _SLINSOLVER_H_
29   	#define _SLINSOLVER_H_
30   	
31   	
32   	#include <assert.h>
33   	#include <string.h>
34   	
35   	#include "soplex/spxdefines.h"
36   	#include "soplex/svector.h"
37   	#include "soplex/ssvector.h"
38   	#include "soplex/dsvector.h"
39   	#include "soplex/didxset.h"
40   	
41   	namespace soplex
42   	{
43   	/**@brief   Sparse Linear Solver virtual base class.
44   	   @ingroup Algo
45   	
46   	   Class SLinSolver provides a class for solving sparse linear systems with
47   	   a matrix \f$A\f$ and arbitrary right-hand side vectors. For doing so, the
48   	   matrix must be first #load%ed to an #SLinSolver object as an array of
49   	   pointers to the \em column \ref SVectorBase<R> "SVectors" of this matrix.
50   	*/
51   	template <class R>
52   	class SLinSolver
53   	{
54   	public:
55   	
56   	   //---------------------------------------
57   	   /**@name Types */
58   	   ///@{
59   	   /// status flags of the SLinSolver class.
60   	   enum Status
61   	   {
62   	      /** The SLinSolver is ready for solving linear systems with the
63   	          loaded matrix */
64   	      OK       = 0,
65   	      /** The loaded matrix allows only for instable solutions to be
66   	          computed */
67   	      INSTABLE = 1,
68   	      /// The loaded matrix is singular.
69   	      SINGULAR = 2,
70   	      /// No matrix has yet been loaded.
71   	      UNLOADED = 4,
72   	      /// An error has occurred.
73   	      ERROR    = 8
74   	   };
75   	   ///@}
76   	
77   	   //---------------------------------------
78   	   /**@name Miscellaneous */
79   	   ///@{
80   	   /// returns the name of the SLinSolver.
81   	   virtual const char* getName() const = 0;
82   	
83   	   /// returns the Status of the SLinSolver.
84   	   virtual Status status() const = 0;
85   	
86   	   /// unloads any matrix.
87   	   virtual void clear() = 0;
88   	
89   	   /// returns current memory consumption.
90   	   virtual int memory() const = 0;
91   	
92   	   /// returns dimension of loaded matrix.
93   	   virtual int dim() const = 0;
94   	
95   	   /// loads \p dim column vectors \p vec into the solver.
96   	   /** Initializes SLinSolver for the solution of linear systems
97   	       with the matrix consisting of \p dim column vectors given in \p vec.
98   	   */
99   	   virtual Status load(const SVectorBase<R>* vec[], int dim) = 0;
100  	
101  	   /// returns a stability number (0: singularity, 1: perfect stability).
102  	   /** Returns a stability parameter between 0 and 1, where 0 indicates
103  	       singularity, while 1 indicates perfect stability.
104  	   */
105  	   virtual R stability() const = 0;
106  	
107  	   /// return estimate for the condition number based on the diagonal of U
108  	   virtual R matrixMetric(int type = 0) const = 0;
109  	
110  	   /// returns statistical information in form of a string.
111  	   virtual std::string statistics() const = 0;
112  	
113  	   /// Substitute column \p idx with \p subst.
114  	   /** The change method is used to modify the loaded matrix by substituting
115  	       column \p idx with the new vector \p subst. One may also pass the
116  	       optional parameter \p eta to the solution of #solveRight() if
117  	       readily  availabble. This may improve on the performance of the update.
118  	   */
119  	   virtual Status change(int idx, const SVectorBase<R>& subst, const SSVectorBase<R>* eta = 0) = 0;
120  	
121  	   /// consistency check.
122  	   virtual bool isConsistent() const = 0;
123  	
124  	   /// get number of factorizations
125  	   virtual int getFactorCount() const = 0;
126  	   ///@}
127  	
128  	
129  	   /**@name Solving linear systems
130  	      For solving linear systems with an SLinSolver object, it must
131  	      have previously been loaded with the matrix to use.
132  	
133  	      Two types of systems can be solved \f$A x = b\f$ and \f$x^T A = b^T\f$.
134  	      Method names related to the first and second type are solveRight() and
135  	      solveLeft(), respectively.
136  	
137  	      The methods receive their right hand-side vector \f$b\f$ as a
138  	      \c const parameter, that will hence be unchanged after termination.
139  	
140  	      Some methods are available with two parameters for right hand-side
141  	      vectors. Then two system are solved in one method invocation. This
142  	      should generally be faster than solving two systems seperately.
143  	
144  	      The result vector(s) are allways given as the first parameter(s). Two
145  	      types of result vectors are supported, VectorBase<R> and SSVectorBase<R> .
146  	   */
147  	   ///@{
148  	   /// Solves \f$Ax=b\f$.
149  	   virtual void solveRight(VectorBase<R>& x, const VectorBase<R>& b) /* const */ = 0;
150  	   /// Solves \f$Ax=b\f$.
151  	   virtual void solveRight(SSVectorBase<R>& x, const SSVectorBase<R>& b) /* const */ = 0;
152  	   virtual void solveRight(SSVectorBase<R>& x, const SVectorBase<R>& b) /* const */ = 0;
153  	
154  	   /** @brief Solves \f$Ax=b\f$.
155  	       Possibly sets up internal data structures suitable for an optimized
156  	       subsequent change() call with \f$b\f$ as entering column.
157  	   */
158  	   virtual void solveRight4update(SSVectorBase<R>& x, const SVectorBase<R>& b) = 0;
159  	
160  	   /// Solves \f$Ax=b\f$ and \f$Ay=d\f$.
161  	   virtual void solve2right4update(SSVectorBase<R>& x,
162  	                                   VectorBase<R>& y,
163  	                                   const SVectorBase<R>& b,
164  	                                   SSVectorBase<R>& d) = 0;
165  	   /// sparse version of solving two systems of equations
166  	   virtual void solve2right4update(SSVectorBase<R>& x,
167  	                                   SSVectorBase<R>& y,
168  	                                   const SVectorBase<R>& b,
169  	                                   SSVectorBase<R>& d) = 0;
170  	   /// Solves \f$Ax=b\f$, \f$Ay=d\f$ and \f$Az=e\f$.
171  	   virtual void solve3right4update(SSVectorBase<R>& x,
172  	                                   VectorBase<R>& y,
173  	                                   VectorBase<R>& z,
174  	                                   const SVectorBase<R>& b,
175  	                                   SSVectorBase<R>& d,
176  	                                   SSVectorBase<R>& e) = 0;
177  	   /// sparse version of solving three systems of equations
178  	   virtual void solve3right4update(SSVectorBase<R>& x,
179  	                                   SSVectorBase<R>& y,
180  	                                   SSVectorBase<R>& z,
181  	                                   const SVectorBase<R>& b,
182  	                                   SSVectorBase<R>& d,
183  	                                   SSVectorBase<R>& e) = 0;
184  	   /// solves \f$x^TA=b^T\f$.
185  	   virtual void solveLeft(VectorBase<R>& x, const VectorBase<R>& b) /* const */ = 0;
186  	   virtual void solveLeft(SSVectorBase<R>& x, const SSVectorBase<R>& b) /* const */ = 0;
187  	   /// sparse version of solving one system of equations with transposed basis matrix
188  	   virtual void solveLeft(SSVectorBase<R>& x, const SVectorBase<R>& b) /* const */ = 0;
189  	   /// solves \f$x^TA=b^T\f$ and \f$x^TA=rhs2^T\f$ internally using \f$rhs2\f$.
190  	   virtual void solveLeft(SSVectorBase<R>& x,
191  	                          VectorBase<R>& two,
192  	                          const SVectorBase<R>& b,
193  	                          SSVectorBase<R>& rhs2) /* const */ = 0;
194  	   /// sparse version of solving two systems of equations with transposed basis matrix
195  	   virtual void solveLeft(SSVectorBase<R>& x,
196  	                          SSVectorBase<R>& two,
197  	                          const SVectorBase<R>& b,
198  	                          SSVectorBase<R>& rhs2) /* const */ = 0;
199  	   /// solves \f$x^TA=b^T\f$, \f$y^TA=d^T\f$ and \f$z^TA=e^T\f$
200  	   virtual void solveLeft(SSVectorBase<R>& x, VectorBase<R>& y, VectorBase<R>& z,
201  	                          const SVectorBase<R>& b, SSVectorBase<R>& d, SSVectorBase<R>& e) = 0;
202  	   /// sparse version of solving three systems of equations with transposed basis matrix
203  	   virtual void solveLeft(SSVectorBase<R>& x, SSVectorBase<R>& y, SSVectorBase<R>& z,
204  	                          const SVectorBase<R>& b, SSVectorBase<R>& d, SSVectorBase<R>& e) = 0;
205  	   ///@}
206  	
207  	
208  	   //---------------------------------------
209  	   /**@name Constructors / Destructors */
210  	   ///@{
211  	   /// default constructor
212  	   SLinSolver()
213  	      : spxout(0)
214  	   {}
215  	   /// destructor
216  	   virtual ~SLinSolver()
217  	   {}
218  	   /// clone function for polymorphism
219  	   virtual SLinSolver<R>* clone() const = 0;
220  	   ///@}
221  	
222  	   /// message handler
223  	   SPxOut* spxout;
224  	
225  	
226  	};
227  	
228  	} // namespace soplex
229  	#endif // _SLINSOLVER_H_
230