|
Belos
Version of the Day
|
00001 //@HEADER 00002 // ************************************************************************ 00003 // 00004 // Belos: Block Linear Solvers Package 00005 // Copyright 2004 Sandia Corporation 00006 // 00007 // Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation, 00008 // the U.S. Government retains certain rights in this software. 00009 // 00010 // Redistribution and use in source and binary forms, with or without 00011 // modification, are permitted provided that the following conditions are 00012 // met: 00013 // 00014 // 1. Redistributions of source code must retain the above copyright 00015 // notice, this list of conditions and the following disclaimer. 00016 // 00017 // 2. Redistributions in binary form must reproduce the above copyright 00018 // notice, this list of conditions and the following disclaimer in the 00019 // documentation and/or other materials provided with the distribution. 00020 // 00021 // 3. Neither the name of the Corporation nor the names of the 00022 // contributors may be used to endorse or promote products derived from 00023 // this software without specific prior written permission. 00024 // 00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY 00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE 00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00036 // 00037 // Questions? Contact Michael A. Heroux (maherou@sandia.gov) 00038 // 00039 // ************************************************************************ 00040 //@HEADER 00041 // 00042 00043 #ifndef BELOS_STATUS_TEST_RESNORM_OUTPUT_HPP 00044 #define BELOS_STATUS_TEST_RESNORM_OUTPUT_HPP 00045 00051 #include <vector> 00052 #include "BelosConfigDefs.hpp" 00053 #include "BelosTypes.hpp" 00054 #include "BelosIteration.hpp" 00055 00056 #include "BelosStatusTest.hpp" 00057 #include "BelosStatusTestCombo.hpp" 00058 #include "BelosStatusTestMaxIters.hpp" 00059 #include "BelosStatusTestResNorm.hpp" 00060 #include "BelosStatusTestOutput.hpp" 00061 00062 namespace Belos { 00063 00073 template <class ScalarType, class MV, class OP> 00074 class StatusTestResNormOutput : public StatusTestOutput<ScalarType,MV,OP> { 00075 00076 typedef MultiVecTraits<ScalarType,MV> MVT; 00077 typedef Belos::StatusTestCombo<ScalarType,MV,OP> StatusTestCombo_t; 00078 typedef Belos::StatusTestResNorm<ScalarType,MV,OP> StatusTestResNorm_t; 00079 typedef Belos::StatusTestMaxIters<ScalarType,MV,OP> StatusTestMaxIters_t; 00080 00081 public: 00083 00084 00100 StatusTestResNormOutput(const Teuchos::RCP<OutputManager<ScalarType> > &printer, 00101 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > test, 00102 int mod = 1, 00103 int printStates = Passed) 00104 : printer_(printer), 00105 state_(Undefined), 00106 headerPrinted_(false), 00107 stateTest_(printStates), 00108 modTest_(mod), 00109 lastNumIters_(-1), 00110 comboType_(0), 00111 numResTests_(0), 00112 blockSize_(1), 00113 currNumRHS_(0), 00114 currLSNum_(0), 00115 numLSDgts_(1), 00116 numIterDgts_(1) 00117 { 00118 // Set the input test. 00119 setChild(test); 00120 } 00121 00123 virtual ~StatusTestResNormOutput() {}; 00125 00127 00128 00145 StatusType checkStatus( Iteration<ScalarType,MV,OP>* solver ) 00146 { 00147 TEUCHOS_TEST_FOR_EXCEPTION(iterTest_ == Teuchos::null,StatusTestError,"StatusTestResNormOutput::checkStatus(): iteration test pointer is null."); 00148 TEUCHOS_TEST_FOR_EXCEPTION(resTestVec_.size() == 0,StatusTestError,"StatusTestResNormOutput::checkStatus(): residual test pointer is null."); 00149 state_ = test_->checkStatus(solver); 00150 00151 // Update some information for the header, if it has not printed or the linear system has changed. 00152 LinearProblem<ScalarType,MV,OP> currProb = solver->getProblem(); 00153 //if (!headerPrinted_ || currLSNum_ != currProb.getLSNumber()) { 00154 if (currLSNum_ != currProb.getLSNumber()) { 00155 currLSNum_ = currProb.getLSNumber(); 00156 blockSize_ = solver->getBlockSize(); 00157 currIdx_ = currProb.getLSIndex(); 00158 currNumRHS_ = currIdx_.size(); 00159 numLSDgts_ = (int)std::floor((double)MVT::GetNumberVecs(*(currProb.getRHS())))+1; 00160 numIterDgts_ = (int)std::floor(std::log10((double)iterTest_->getMaxIters()))+1; 00161 } 00162 // Print out current iteration information if it hasn't already been printed, or the status has changed 00163 if (((iterTest_->getNumIters() % modTest_ == 0) && (iterTest_->getNumIters()!=lastNumIters_)) || (state_ == Passed)) { 00164 lastNumIters_ = iterTest_->getNumIters(); 00165 if ( (state_ & stateTest_) == state_) { 00166 if ( printer_->isVerbosity(StatusTestDetails) ) { 00167 print( printer_->stream(StatusTestDetails) ); 00168 } 00169 else if ( printer_->isVerbosity(Debug) ) { 00170 print( printer_->stream(Debug) ); 00171 } 00172 } 00173 } 00174 00175 return state_; 00176 } 00177 00179 StatusType getStatus() const { 00180 return state_; 00181 } 00183 00184 00186 00187 00190 void setOutputManager(const Teuchos::RCP<OutputManager<ScalarType> > &printer) { printer_ = printer; } 00191 00194 void setOutputFrequency(int mod) { modTest_ = mod; } 00195 00200 void setChild(Teuchos::RCP<StatusTest<ScalarType,MV,OP> > test) { 00201 00202 // First check to see if this test is a combination test 00203 Teuchos::RCP<StatusTestCombo_t> comboTest = Teuchos::rcp_dynamic_cast<StatusTestCombo_t>(test); 00204 TEUCHOS_TEST_FOR_EXCEPTION(comboTest == Teuchos::null,StatusTestError,"StatusTestResNormOutput(): test must be a Belos::StatusTestCombo."); 00205 std::vector<Teuchos::RCP<StatusTest<ScalarType,MV,OP> > > tmpVec = comboTest->getStatusTests(); 00206 00207 // Get the number of tests. 00208 int numTests = tmpVec.size(); 00209 00210 // Find the maximum iteration and residual tests 00211 for (int i=0; i<numTests; ++i) { 00212 00213 // Check if this is a maximum iteration test. 00214 Teuchos::RCP<StatusTestMaxIters_t> tmpItrTest = Teuchos::rcp_dynamic_cast<StatusTestMaxIters_t>(tmpVec[i]); 00215 if (tmpItrTest != Teuchos::null) { 00216 iterTest_ = tmpItrTest; 00217 continue; 00218 } 00219 00220 // Check if this is a single residual test 00221 Teuchos::RCP<StatusTestResNorm_t> tmpResTest = Teuchos::rcp_dynamic_cast<StatusTestResNorm_t>(tmpVec[i]); 00222 // If the residual status test is a single test, put in the vector 00223 if (tmpResTest != Teuchos::null) { 00224 numResTests_ = 1; 00225 resTestVec_.resize( numResTests_ ); 00226 resTestVec_[0] = tmpResTest; 00227 continue; 00228 } 00229 00230 // Check if the residual test is a combination of several StatusTestResNorm objects. 00231 Teuchos::RCP<StatusTestCombo_t> tmpComboTest = Teuchos::rcp_dynamic_cast<StatusTestCombo_t>(tmpVec[i]); 00232 TEUCHOS_TEST_FOR_EXCEPTION(tmpComboTest == Teuchos::null,StatusTestError,"StatusTestResNormOutput(): test must be Belos::StatusTest[MaxIters|ResNorm|Combo]."); 00233 tmpVec = tmpComboTest->getStatusTests(); 00234 comboType_ = tmpComboTest->getComboType(); 00235 numResTests_ = tmpVec.size(); 00236 resTestVec_.resize( numResTests_ ); 00237 for (int j=0; j<numResTests_; ++j) { 00238 tmpResTest = Teuchos::rcp_dynamic_cast<StatusTestResNorm_t>(tmpVec[j]); 00239 TEUCHOS_TEST_FOR_EXCEPTION(tmpResTest == Teuchos::null,StatusTestError,"StatusTestResNormOutput(): test must be a vector of Belos::StatusTestResNorm."); 00240 resTestVec_[j] = tmpResTest; 00241 } 00242 } 00243 00244 // Keep the pointer to the new test and reset the state to Undefined. 00245 test_ = test; 00246 state_ = Undefined; 00247 00248 } 00249 00251 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > getChild() const { 00252 return test_; 00253 } 00254 00257 void setSolverDesc(const std::string& solverDesc) { solverDesc_ = solverDesc; } 00258 00261 void setPrecondDesc(const std::string& precondDesc) { precondDesc_ = precondDesc; } 00263 00264 00266 00267 00272 void reset() { 00273 state_ = Undefined; 00274 test_->reset(); 00275 lastNumIters_ = -1; 00276 headerPrinted_ = false; 00277 } 00278 00280 00283 void resetNumCalls() {} 00284 00286 00288 00289 00291 void print(std::ostream& os, int indent = 0) const { 00292 std::string ind(indent,' '); 00293 std::string starLine(55,'*'); 00294 std::string starFront(5,'*'); 00295 00296 std::ios_base::fmtflags osFlags(os.flags()); 00297 00298 os.setf(std::ios::scientific, std::ios::floatfield); 00299 os.precision(6); 00300 00301 // Print header if this is the first call to this output status test. 00302 if (!headerPrinted_) { 00303 os << std::endl << ind << starLine << std::endl; 00304 os << ind << starFront << " Belos Iterative Solver: " << solverDesc_ << std::endl; 00305 if (precondDesc_ != "") 00306 os << ind << starFront << " Preconditioner: " << precondDesc_ << std::endl; 00307 os << ind << starFront << " Maximum Iterations: " << iterTest_->getMaxIters() << std::endl; 00308 os << ind << starFront << " Block Size: " << blockSize_ << std::endl; 00309 if (numResTests_ > 1) { 00310 os << ind << starFront << " Residual Tests (" 00311 << ((comboType_ == StatusTestCombo_t::OR) ? "OR" : (comboType_ == StatusTestCombo_t::AND) ? "AND" :"SEQ") 00312 << "): " << std::endl; 00313 } else { 00314 os << ind << starFront << " Residual Test: " << std::endl; 00315 } 00316 for (int i=0; i<numResTests_; ++i) { 00317 os << ind << starFront << " Test " << i+1 << " : " << resTestVec_[i]->description() << std::endl; 00318 } 00319 os << ind << starLine << std::endl; 00320 headerPrinted_ = true; 00321 } 00322 00323 // Print out residuals for each residual test. 00324 os.setf(std::ios_base::right, std::ios_base::adjustfield); 00325 std::string ind2( 7 + numIterDgts_, ' ' ); 00326 os << ind << "Iter " << std::setw(numIterDgts_) << iterTest_->getNumIters() << ", "; 00327 for (int i=0; i<currNumRHS_; ++i) { 00328 if ( i > 0 && currIdx_[i]!=-1 ) { 00329 // Put in space where 'Iter :' is in the previous lines 00330 os << ind << ind2; 00331 } 00332 os << "[" << std::setw(numLSDgts_) << currIdx_[i]+1 << "] : "; 00333 for (int j=0; j<numResTests_; ++j) { 00334 if ( resTestVec_[j]->getStatus() != Undefined && currIdx_[i]!=-1 ) { 00335 os << std::setw(15) << (*resTestVec_[j]->getTestValue())[currIdx_[i]]; 00336 } else { 00337 os << std::setw(15) << "---"; 00338 } 00339 } 00340 os << std::endl; 00341 } 00342 // reset os format 00343 os.flags(osFlags); 00344 } 00345 00347 00348 private: 00349 // Output manager. 00350 Teuchos::RCP<OutputManager<ScalarType> > printer_; 00351 00352 // Overall status test. 00353 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > test_; 00354 00355 // Iteration test (as passed in). 00356 Teuchos::RCP<StatusTestMaxIters<ScalarType,MV,OP> > iterTest_; 00357 00359 std::vector<Teuchos::RCP<StatusTestResNorm<ScalarType,MV,OP> > > resTestVec_; 00360 00361 std::string solverDesc_; 00362 std::string precondDesc_; 00363 std::vector<int> currIdx_; 00364 StatusType state_; 00365 mutable bool headerPrinted_; 00366 int stateTest_, modTest_; 00367 int lastNumIters_, comboType_; 00368 int numResTests_, blockSize_; 00369 int currNumRHS_, currLSNum_; 00370 int numLSDgts_, numIterDgts_; 00371 }; 00372 00373 } // end of Belos namespace 00374 00375 #endif /* BELOS_STATUS_TEST_RESNORM_OUTPUT_HPP */
1.7.6.1