Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 #include "SundanceLinearSolveDriver.hpp"
00043 #include "PlayaLinearSolverDecl.hpp"
00044 #include "SundanceOut.hpp"
00045 #include "PlayaTabs.hpp"
00046
00047
00048 #ifndef HAVE_TEUCHOS_EXPLICIT_INSTANTIATION
00049 #include "PlayaLinearSolverImpl.hpp"
00050 #endif
00051
00052
00053
00054
00055 using namespace Sundance;
00056 using namespace Sundance;
00057 using namespace Sundance;
00058 using namespace Sundance;
00059 using namespace Sundance;
00060 using namespace Sundance;
00061 using namespace Sundance;
00062 using namespace Teuchos;
00063 using namespace Playa;
00064 using namespace std;
00065
00066
00067 SolverState<double>
00068 LinearSolveDriver::solve(const LinearSolver<double>& solver,
00069 const LinearOperator<double>& A,
00070 const Array<Vector<double> >& rhs,
00071 const Array<RCP<DiscreteSpace> >& solutionSpace,
00072 const Array<Array<string> >& names,
00073 int verb,
00074 Expr& soln) const
00075 {
00076 Tabs tab(0);
00077 Array<Vector<double> > solnVec(rhs.size());
00078 SolverState<double> state;
00079
00080 for (int i=0; i<rhs.size(); i++)
00081 {
00082 Tabs tab1;
00083
00084 solnVec[i] = rhs[i].copy();
00085
00086 SUNDANCE_MSG2(verb, tab1 << "solving with RHS #" << i
00087 << " of " << rhs.size());
00088
00089 state = solver.solve(A, rhs[i], solnVec[i]);
00090
00091 SUNDANCE_MSG2(verb, tab1 << "solve completed with status="
00092 << state.stateDescription());
00093
00094
00095 if (state.finalState() != SolveConverged)
00096 {
00097 TeuchosOStringStream ss;
00098 ss << "Solve failed! state = "
00099 << state.stateDescription()
00100 << "\nmessage=" << state.finalMsg()
00101 << "\niters taken = " << state.finalIters()
00102 << "\nfinal residual = " << state.finalResid();
00103
00104
00105 if (dumpBadMatrix())
00106 {
00107 if (A.ptr().get() != 0)
00108 {
00109 ofstream osA(badMatrixFilename().c_str());
00110 A.print(osA);
00111 ss << "\nmatrix written to " << badMatrixFilename();
00112 }
00113 else
00114 {
00115 ss << "\nthe matrix is null! Evil is afoot in your code...";
00116 }
00117 if (rhs[i].ptr().get() != 0)
00118 {
00119 ofstream osb(badVectorFilename().c_str());
00120 rhs[i].print(osb);
00121 ss << "\nRHS vector written to " << badVectorFilename();
00122 }
00123 else
00124 {
00125 ss << "\nthe RHS vector is null! Evil is afoot in your code...";
00126 }
00127 }
00128
00129
00130 TEUCHOS_TEST_FOR_EXCEPTION(solveFailureIsFatal(),
00131 std::runtime_error, TEUCHOS_OSTRINGSTREAM_GET_C_STR(ss));
00132
00133
00134 return state;
00135 }
00136 }
00137
00138
00139 if (soln.ptr().get()==0)
00140 {
00141 soln = formSolutionExpr(solnVec, solutionSpace, names, verb);
00142 }
00143 else
00144 {
00145 writeIntoSolutionExpr(solnVec, soln, verb);
00146 }
00147
00148 return state;
00149
00150 }
00151
00152
00153
00154 Expr LinearSolveDriver::formSolutionExpr(
00155 const Array<Vector<double> >& solnVector,
00156 const Array<RCP<DiscreteSpace> >& solutionSpace,
00157 const Array<Array<string> >& names,
00158 int verb) const
00159 {
00160 Array<Expr> cols(solnVector.size());
00161
00162 for (int m=0; m<solnVector.size(); m++)
00163 {
00164 Array<Expr> col(solutionSpace.size());
00165
00166 for (int i=0; i<col.size(); i++)
00167 {
00168 std::string name = names[m][i];
00169 if (col.size() > 1) name += "[" + Teuchos::toString(i) + "]";
00170 col[i] = new DiscreteFunction(*(solutionSpace[i]),
00171 solnVector[m].getBlock(i), name);
00172 }
00173 if (col.size() > 1)
00174 {
00175 cols[m] = new ListExpr(col);
00176 }
00177 else
00178 {
00179 cols[m] = col[0];
00180 }
00181 }
00182
00183 if (cols.size() > 1)
00184 {
00185 return new ListExpr(cols);;
00186 }
00187 else
00188 {
00189 return cols[0];
00190 }
00191 }
00192
00193
00194 void LinearSolveDriver::writeIntoSolutionExpr(
00195 const Array<Vector<double> >& solnVector,
00196 Expr soln,
00197 int verb) const
00198 {
00199 #ifdef BLAH
00200 TEUCHOS_TEST_FOR_EXCEPTION(soln.size() != solnVector.size(),
00201 std::runtime_error,
00202 "soln=" << soln << " soln.size()=" << soln.size() << " while solnVector.size()=" << solnVector.size());
00203 #endif
00204 for (int i=0; i<solnVector.size(); i++)
00205 {
00206 Expr u = soln[i];
00207 setDiscreteFunctionVector(u, solnVector[i]);
00208 }
00209 }