42 #ifndef ANASAZI_LOBPCG_SOLMGR_HPP
43 #define ANASAZI_LOBPCG_SOLMGR_HPP
68 #include "Teuchos_BLAS.hpp"
69 #include "Teuchos_TimeMonitor.hpp"
70 #include "Teuchos_FancyOStream.hpp"
172 template<
class ScalarType,
class MV,
class OP>
178 typedef Teuchos::ScalarTraits<ScalarType> SCT;
179 typedef typename Teuchos::ScalarTraits<ScalarType>::magnitudeType MagnitudeType;
180 typedef Teuchos::ScalarTraits<MagnitudeType> MT;
215 Teuchos::ParameterList &pl );
240 Teuchos::Array<Teuchos::RCP<Teuchos::Time> >
getTimers()
const {
241 return Teuchos::tuple(_timerSolve, _timerLocking);
299 Teuchos::RCP<Eigenproblem<ScalarType,MV,OP> > problem_;
301 std::string whch_, ortho_;
303 MagnitudeType convtol_, locktol_;
304 int maxIters_, numIters_;
306 bool relconvtol_, rellocktol_;
313 Teuchos::RCP<LOBPCGState<ScalarType,MV> > state_;
314 enum ResType convNorm_, lockNorm_;
317 Teuchos::RCP<Teuchos::Time> _timerSolve, _timerLocking;
319 Teuchos::RCP<Teuchos::FancyOStream> osp_;
321 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > globalTest_;
322 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > lockingTest_;
323 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > debugTest_;
328 template<
class ScalarType,
class MV,
class OP>
331 Teuchos::ParameterList &pl ) :
335 convtol_(MT::prec()),
348 #ifdef ANASAZI_TEUCHOS_TIME_MONITOR
349 , _timerSolve(Teuchos::TimeMonitor::getNewTimer(
"Anasazi: LOBPCGSolMgr::solve()")),
350 _timerLocking(Teuchos::TimeMonitor::getNewTimer(
"Anasazi: LOBPCGSolMgr locking"))
353 TEUCHOS_TEST_FOR_EXCEPTION(problem_ == Teuchos::null, std::invalid_argument,
"Problem not given to solver manager.");
354 TEUCHOS_TEST_FOR_EXCEPTION(!problem_->isProblemSet(), std::invalid_argument,
"Problem not set.");
355 TEUCHOS_TEST_FOR_EXCEPTION(!problem_->isHermitian(), std::invalid_argument,
"Problem not symmetric.");
356 TEUCHOS_TEST_FOR_EXCEPTION(problem_->getInitVec() == Teuchos::null,std::invalid_argument,
"Problem does not contain initial vectors to clone from.");
362 whch_ = pl.get(
"Which",whch_);
363 TEUCHOS_TEST_FOR_EXCEPTION(whch_ !=
"SM" && whch_ !=
"LM" && whch_ !=
"SR" && whch_ !=
"LR",
364 std::invalid_argument,
"Anasazi::LOBPCGSolMgr: Invalid sorting string.");
367 ortho_ = pl.get(
"Orthogonalization",ortho_);
368 if (ortho_ !=
"DGKS" && ortho_ !=
"SVQB") {
373 convtol_ = pl.get(
"Convergence Tolerance",convtol_);
374 relconvtol_ = pl.get(
"Relative Convergence Tolerance",relconvtol_);
375 strtmp = pl.get(
"Convergence Norm",std::string(
"2"));
377 convNorm_ = RES_2NORM;
379 else if (strtmp ==
"M") {
380 convNorm_ = RES_ORTH;
383 TEUCHOS_TEST_FOR_EXCEPTION(
true, std::invalid_argument,
384 "Anasazi::LOBPCGSolMgr: Invalid Convergence Norm.");
389 useLocking_ = pl.get(
"Use Locking",useLocking_);
390 rellocktol_ = pl.get(
"Relative Locking Tolerance",rellocktol_);
392 locktol_ = convtol_/10;
393 locktol_ = pl.get(
"Locking Tolerance",locktol_);
394 strtmp = pl.get(
"Locking Norm",std::string(
"2"));
396 lockNorm_ = RES_2NORM;
398 else if (strtmp ==
"M") {
399 lockNorm_ = RES_ORTH;
402 TEUCHOS_TEST_FOR_EXCEPTION(
true, std::invalid_argument,
403 "Anasazi::LOBPCGSolMgr: Invalid Locking Norm.");
407 maxIters_ = pl.get(
"Maximum Iterations",maxIters_);
410 blockSize_ = pl.get(
"Block Size",problem_->getNEV());
411 TEUCHOS_TEST_FOR_EXCEPTION(blockSize_ <= 0, std::invalid_argument,
412 "Anasazi::LOBPCGSolMgr: \"Block Size\" must be strictly positive.");
416 maxLocked_ = pl.get(
"Max Locked",problem_->getNEV());
421 if (maxLocked_ == 0) {
424 TEUCHOS_TEST_FOR_EXCEPTION(maxLocked_ < 0, std::invalid_argument,
425 "Anasazi::LOBPCGSolMgr: \"Max Locked\" must be positive.");
426 TEUCHOS_TEST_FOR_EXCEPTION(maxLocked_ + blockSize_ < problem_->getNEV(),
427 std::invalid_argument,
428 "Anasazi::LOBPCGSolMgr: Not enough storage space for requested number of eigenpairs.");
431 lockQuorum_ = pl.get(
"Locking Quorum",lockQuorum_);
432 TEUCHOS_TEST_FOR_EXCEPTION(lockQuorum_ <= 0,
433 std::invalid_argument,
434 "Anasazi::LOBPCGSolMgr: \"Locking Quorum\" must be strictly positive.");
438 fullOrtho_ = pl.get(
"Full Ortho",fullOrtho_);
442 osProc_ = pl.get(
"Output Processor", osProc_);
445 if (pl.isParameter(
"Output Stream")) {
446 osp_ = Teuchos::getParameter<Teuchos::RCP<Teuchos::FancyOStream> >(pl,
"Output Stream");
453 if (pl.isParameter(
"Verbosity")) {
454 if (Teuchos::isParameterType<int>(pl,
"Verbosity")) {
455 verbosity_ = pl.get(
"Verbosity", verbosity_);
457 verbosity_ = (int)Teuchos::getParameter<Anasazi::MsgType>(pl,
"Verbosity");
462 recover_ = pl.get(
"Recover",recover_);
465 if (pl.isParameter(
"Init")) {
466 state_ = Teuchos::getParameter<Teuchos::RCP<Anasazi::LOBPCGState<ScalarType,MV> > >(pl,
"Init");
472 template<
class ScalarType,
class MV,
class OP>
478 const int nev = problem_->getNEV();
494 Teuchos::RCP<StatusTestMaxIters<ScalarType,MV,OP> > maxtest;
499 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > convtest;
500 if (globalTest_ == Teuchos::null) {
504 convtest = globalTest_;
506 Teuchos::RCP<StatusTestWithOrdering<ScalarType,MV,OP> > ordertest
509 Teuchos::RCP<StatusTest<ScalarType,MV,OP> > locktest;
511 if (lockingTest_ == Teuchos::null) {
515 locktest = lockingTest_;
519 Teuchos::Array<Teuchos::RCP<StatusTest<ScalarType,MV,OP> > > alltests;
520 alltests.push_back(ordertest);
521 if (locktest != Teuchos::null) alltests.push_back(locktest);
522 if (debugTest_ != Teuchos::null) alltests.push_back(debugTest_);
523 if (maxtest != Teuchos::null) alltests.push_back(maxtest);
524 Teuchos::RCP<StatusTestCombo<ScalarType,MV,OP> > combotest
527 Teuchos::RCP<StatusTestOutput<ScalarType,MV,OP> > outputtest;
528 if ( printer->isVerbosity(
Debug) ) {
537 Teuchos::RCP<MatOrthoManager<ScalarType,MV,OP> > ortho;
538 if (ortho_==
"SVQB") {
540 }
else if (ortho_==
"DGKS") {
543 TEUCHOS_TEST_FOR_EXCEPTION(ortho_!=
"SVQB"&&ortho_!=
"DGKS",std::logic_error,
"Anasazi::LOBPCGSolMgr::solve(): Invalid orthogonalization type.");
548 Teuchos::ParameterList plist;
549 plist.set(
"Block Size",blockSize_);
550 plist.set(
"Full Ortho",fullOrtho_);
554 Teuchos::RCP<LOBPCG<ScalarType,MV,OP> > lobpcg_solver
557 Teuchos::RCP< const MV > probauxvecs = problem_->getAuxVecs();
558 if (probauxvecs != Teuchos::null) {
559 lobpcg_solver->setAuxVecs( Teuchos::tuple< Teuchos::RCP<const MV> >(probauxvecs) );
566 int curNumLocked = 0;
567 Teuchos::RCP<MV> lockvecs;
569 lockvecs = MVT::Clone(*problem_->getInitVec(),maxLocked_);
571 std::vector<MagnitudeType> lockvals;
580 Teuchos::RCP<MV> workMV;
581 if (fullOrtho_ ==
false && recover_ ==
true) {
582 workMV = MVT::Clone(*problem_->getInitVec(),2*3*blockSize_);
584 else if (useLocking_) {
585 if (problem_->getM() != Teuchos::null) {
586 workMV = MVT::Clone(*problem_->getInitVec(),4*blockSize_);
589 workMV = MVT::Clone(*problem_->getInitVec(),2*blockSize_);
596 problem_->setSolution(sol);
599 if (state_ != Teuchos::null) {
600 lobpcg_solver->initialize(*state_);
605 #ifdef ANASAZI_TEUCHOS_TIME_MONITOR
606 Teuchos::TimeMonitor slvtimer(*_timerSolve);
612 lobpcg_solver->iterate();
619 if (debugTest_ != Teuchos::null && debugTest_->getStatus() ==
Passed) {
620 throw AnasaziError(
"Anasazi::LOBPCGSolMgr::solve(): User-specified debug status test returned Passed.");
627 else if (ordertest->getStatus() ==
Passed || (maxtest != Teuchos::null && maxtest->getStatus() ==
Passed) ) {
638 else if (locktest != Teuchos::null && locktest->getStatus() ==
Passed) {
640 #ifdef ANASAZI_TEUCHOS_TIME_MONITOR
641 Teuchos::TimeMonitor lcktimer(*_timerLocking);
645 TEUCHOS_TEST_FOR_EXCEPTION(locktest->howMany() <= 0,std::logic_error,
646 "Anasazi::LOBPCGSolMgr::solve(): status test mistake: howMany() non-positive.");
647 TEUCHOS_TEST_FOR_EXCEPTION(locktest->howMany() != (int)locktest->whichVecs().size(),std::logic_error,
648 "Anasazi::LOBPCGSolMgr::solve(): status test mistake: howMany() not consistent with whichVecs().");
649 TEUCHOS_TEST_FOR_EXCEPTION(curNumLocked == maxLocked_,std::logic_error,
650 "Anasazi::LOBPCGSolMgr::solve(): status test mistake: locking not deactivated.");
652 int numnew = locktest->howMany();
653 std::vector<int> indnew = locktest->whichVecs();
656 if (curNumLocked + numnew > maxLocked_) {
657 numnew = maxLocked_ - curNumLocked;
658 indnew.resize(numnew);
663 bool hadP = lobpcg_solver->hasP();
667 printer->print(
Debug,
"Locking vectors: ");
668 for (
unsigned int i=0; i<indnew.size(); i++) {printer->stream(
Debug) <<
" " << indnew[i];}
669 printer->print(
Debug,
"\n");
671 std::vector<MagnitudeType> newvals(numnew);
672 Teuchos::RCP<const MV> newvecs;
676 newvecs = MVT::CloneView(*lobpcg_solver->getRitzVectors(),indnew);
678 std::vector<Value<ScalarType> > allvals = lobpcg_solver->getRitzValues();
679 for (
int i=0; i<numnew; i++) {
680 newvals[i] = allvals[indnew[i]].realpart;
685 std::vector<int> indlock(numnew);
686 for (
int i=0; i<numnew; i++) indlock[i] = curNumLocked+i;
687 MVT::SetBlock(*newvecs,indlock,*lockvecs);
688 newvecs = Teuchos::null;
691 lockvals.insert(lockvals.end(),newvals.begin(),newvals.end());
692 curNumLocked += numnew;
695 std::vector<int> indlock(curNumLocked);
696 for (
int i=0; i<curNumLocked; i++) indlock[i] = i;
697 Teuchos::RCP<const MV> curlocked = MVT::CloneView(*lockvecs,indlock);
698 if (probauxvecs != Teuchos::null) {
699 lobpcg_solver->setAuxVecs( Teuchos::tuple< Teuchos::RCP<const MV> >(probauxvecs,curlocked) );
702 lobpcg_solver->setAuxVecs( Teuchos::tuple< Teuchos::RCP<const MV> >(curlocked) );
706 ordertest->setAuxVals(lockvals);
710 Teuchos::RCP<MV> newstateX, newstateMX, newstateP, newstateMP;
715 std::vector<int> bsind(blockSize_);
716 for (
int i=0; i<blockSize_; i++) bsind[i] = i;
717 newstateX = MVT::CloneViewNonConst(*workMV,bsind);
718 MVT::SetBlock(*state.
X,bsind,*newstateX);
720 if (state.
MX != Teuchos::null) {
721 std::vector<int> block3(blockSize_);
722 for (
int i=0; i<blockSize_; i++) block3[i] = 2*blockSize_+i;
723 newstateMX = MVT::CloneViewNonConst(*workMV,block3);
724 MVT::SetBlock(*state.
MX,bsind,*newstateMX);
729 Teuchos::RCP<MV> newX = MVT::CloneViewNonConst(*newstateX,indnew);
730 MVT::MvRandom(*newX);
732 if (newstateMX != Teuchos::null) {
733 Teuchos::RCP<MV> newMX = MVT::CloneViewNonConst(*newstateMX,indnew);
734 OPT::Apply(*problem_->getM(),*newX,*newMX);
738 Teuchos::Array<Teuchos::RCP<const MV> > curauxvecs = lobpcg_solver->getAuxVecs();
739 Teuchos::Array<Teuchos::RCP<Teuchos::SerialDenseMatrix<int,ScalarType> > > dummyC;
741 ortho->projectAndNormalizeMat(*newstateX,curauxvecs,dummyC,Teuchos::null,newstateMX);
746 std::vector<int> block2(blockSize_);
747 for (
int i=0; i<blockSize_; i++) block2[i] = blockSize_+i;
748 newstateP = MVT::CloneViewNonConst(*workMV,block2);
749 MVT::SetBlock(*state.
P,bsind,*newstateP);
751 if (state.
MP != Teuchos::null) {
752 std::vector<int> block4(blockSize_);
753 for (
int i=0; i<blockSize_; i++) block4[i] = 3*blockSize_+i;
754 newstateMP = MVT::CloneViewNonConst(*workMV,block4);
755 MVT::SetBlock(*state.
MP,bsind,*newstateMP);
760 curauxvecs.push_back(newstateX);
761 ortho->projectAndNormalizeMat(*newstateP,curauxvecs,dummyC,Teuchos::null,newstateMP);
765 ortho->projectAndNormalizeMat(*newstateP,curauxvecs,dummyC,Teuchos::null,newstateMP);
770 newstate.
X = newstateX;
771 newstate.
MX = newstateMX;
772 newstate.
P = newstateP;
773 newstate.
MP = newstateMP;
774 lobpcg_solver->initialize(newstate);
777 if (curNumLocked == maxLocked_) {
779 combotest->removeTest(locktest);
783 TEUCHOS_TEST_FOR_EXCEPTION(
true,std::logic_error,
"Anasazi::LOBPCGSolMgr::solve(): Invalid return from lobpcg_solver::iterate().");
792 if (fullOrtho_==
true || recover_==
false) {
796 printer->stream(
Warnings) <<
"Error! Caught LOBPCGRitzFailure at iteration " << lobpcg_solver->getNumIters() << std::endl
797 <<
"Will not try to recover." << std::endl;
800 printer->stream(
Warnings) <<
"Error! Caught LOBPCGRitzFailure at iteration " << lobpcg_solver->getNumIters() << std::endl
801 <<
"Full orthogonalization is off; will try to recover." << std::endl;
807 Teuchos::RCP<MV> restart, Krestart, Mrestart;
808 int localsize = lobpcg_solver->hasP() ? 3*blockSize_ : 2*blockSize_;
809 bool hasM = problem_->getM() != Teuchos::null;
811 std::vector<int> recind(localsize);
812 for (
int i=0; i<localsize; i++) recind[i] = i;
813 restart = MVT::CloneViewNonConst(*workMV,recind);
816 std::vector<int> recind(localsize);
817 for (
int i=0; i<localsize; i++) recind[i] = localsize+i;
818 Krestart = MVT::CloneViewNonConst(*workMV,recind);
831 std::vector<int> blk1(blockSize_);
832 for (
int i=0; i < blockSize_; i++) blk1[i] = i;
833 MVT::SetBlock(*curstate.
X,blk1,*restart);
837 MVT::SetBlock(*curstate.
MX,blk1,*Mrestart);
843 std::vector<int> blk2(blockSize_);
844 for (
int i=0; i < blockSize_; i++) blk2[i] = blockSize_+i;
845 MVT::SetBlock(*curstate.
H,blk2,*restart);
849 MVT::SetBlock(*curstate.
MH,blk2,*Mrestart);
853 if (localsize == 3*blockSize_) {
854 std::vector<int> blk3(blockSize_);
855 for (
int i=0; i < blockSize_; i++) blk3[i] = 2*blockSize_+i;
856 MVT::SetBlock(*curstate.
P,blk3,*restart);
860 MVT::SetBlock(*curstate.
MP,blk3,*Mrestart);
864 Teuchos::Array<Teuchos::RCP<Teuchos::SerialDenseMatrix<int,ScalarType> > > dummyC;
865 Teuchos::Array<Teuchos::RCP<const MV> > Q;
867 if (curNumLocked > 0) {
868 std::vector<int> indlock(curNumLocked);
869 for (
int i=0; i<curNumLocked; i++) indlock[i] = i;
870 Teuchos::RCP<const MV> curlocked = MVT::CloneView(*lockvecs,indlock);
871 Q.push_back(curlocked);
873 if (probauxvecs != Teuchos::null) {
874 Q.push_back(probauxvecs);
877 int rank = ortho->projectAndNormalizeMat(*restart,Q,dummyC,Teuchos::null,Mrestart);
878 if (rank < blockSize_) {
880 printer->stream(
Errors) <<
"Error! Recovered basis only rank " << rank <<
". Block size is " << blockSize_ <<
".\n"
881 <<
"Recovery failed." << std::endl;
885 if (rank < localsize) {
887 std::vector<int> redind(localsize);
888 for (
int i=0; i<localsize; i++) redind[i] = i;
890 restart = MVT::CloneViewNonConst(*restart,redind);
891 Krestart = MVT::CloneViewNonConst(*Krestart,redind);
899 Teuchos::SerialDenseMatrix<int,ScalarType> KK(localsize,localsize), MM(localsize,localsize), S(localsize,localsize);
900 std::vector<MagnitudeType> theta(localsize);
904 MVT::MvTransMv(1.0,*restart,*Mrestart,MM);
907 OPT::Apply(*problem_->getOperator(),*restart,*Krestart);
910 MVT::MvTransMv(1.0,*restart,*Krestart,KK);
912 msutils::directSolver(localsize,KK,Teuchos::rcpFromRef(MM),S,theta,rank,1);
913 if (rank < blockSize_) {
914 printer->stream(
Errors) <<
"Error! Recovered basis of rank " << rank <<
" produced only " << rank <<
"ritz vectors.\n"
915 <<
"Block size is " << blockSize_ <<
".\n"
916 <<
"Recovery failed." << std::endl;
923 Teuchos::BLAS<int,ScalarType> blas;
924 std::vector<int> order(rank);
926 sorter->sort( theta, Teuchos::rcpFromRef(order),rank );
928 Teuchos::SerialDenseMatrix<int,ScalarType> curS(Teuchos::View,S,rank,rank);
929 msutils::permuteVectors(order,curS);
932 Teuchos::SerialDenseMatrix<int,ScalarType> S1(Teuchos::View,S,localsize,blockSize_);
936 Teuchos::RCP<MV> newX;
938 std::vector<int> bsind(blockSize_);
939 for (
int i=0; i<blockSize_; i++) bsind[i] = i;
940 newX = MVT::CloneViewNonConst(*Krestart,bsind);
942 MVT::MvTimesMatAddMv(1.0,*restart,S1,0.0,*newX);
945 theta.resize(blockSize_);
946 newstate.
T = Teuchos::rcpFromRef(theta);
948 lobpcg_solver->initialize(newstate);
952 <<
"Anasazi::LOBPCGSolMgr::solve() caught unexpected exception from Anasazi::LOBPCG::iterate() at iteration " << lobpcg_solver->getNumIters() << std::endl
953 << err.what() << std::endl
954 <<
"Anasazi::LOBPCGSolMgr::solve() returning Unconverged with no solutions." << std::endl;
960 sol.
numVecs = ordertest->howMany();
962 sol.
Evecs = MVT::Clone(*problem_->getInitVec(),sol.
numVecs);
965 std::vector<MagnitudeType> vals(sol.
numVecs);
968 std::vector<int> which = ordertest->whichVecs();
972 std::vector<int> inlocked(0), insolver(0);
973 for (
unsigned int i=0; i<which.size(); i++) {
975 TEUCHOS_TEST_FOR_EXCEPTION(which[i] >= blockSize_,std::logic_error,
"Anasazi::LOBPCGSolMgr::solve(): positive indexing mistake from ordertest.");
976 insolver.push_back(which[i]);
980 TEUCHOS_TEST_FOR_EXCEPTION(which[i] < -curNumLocked,std::logic_error,
"Anasazi::LOBPCGSolMgr::solve(): negative indexing mistake from ordertest.");
981 inlocked.push_back(which[i] + curNumLocked);
985 TEUCHOS_TEST_FOR_EXCEPTION(insolver.size() + inlocked.size() != (
unsigned int)sol.
numVecs,std::logic_error,
"Anasazi::LOBPCGSolMgr::solve(): indexing mistake.");
988 if (insolver.size() > 0) {
990 int lclnum = insolver.size();
991 std::vector<int> tosol(lclnum);
992 for (
int i=0; i<lclnum; i++) tosol[i] = i;
993 Teuchos::RCP<const MV> v = MVT::CloneView(*lobpcg_solver->getRitzVectors(),insolver);
994 MVT::SetBlock(*v,tosol,*sol.
Evecs);
996 std::vector<Value<ScalarType> > fromsolver = lobpcg_solver->getRitzValues();
997 for (
unsigned int i=0; i<insolver.size(); i++) {
998 vals[i] = fromsolver[insolver[i]].realpart;
1003 if (inlocked.size() > 0) {
1004 int solnum = insolver.size();
1006 int lclnum = inlocked.size();
1007 std::vector<int> tosol(lclnum);
1008 for (
int i=0; i<lclnum; i++) tosol[i] = solnum + i;
1009 Teuchos::RCP<const MV> v = MVT::CloneView(*lockvecs,inlocked);
1010 MVT::SetBlock(*v,tosol,*sol.
Evecs);
1012 for (
unsigned int i=0; i<inlocked.size(); i++) {
1013 vals[i+solnum] = lockvals[inlocked[i]];
1019 std::vector<int> order(sol.
numVecs);
1020 sorter->sort( vals, Teuchos::rcpFromRef(order), sol.
numVecs);
1022 for (
int i=0; i<sol.
numVecs; i++) {
1023 sol.
Evals[i].realpart = vals[i];
1024 sol.
Evals[i].imagpart = MT::zero();
1036 lobpcg_solver->currentStatus(printer->stream(
FinalSummary));
1039 #ifdef ANASAZI_TEUCHOS_TIME_MONITOR
1041 Teuchos::TimeMonitor::summarize( printer->stream(
TimingDetails ) );
1045 problem_->setSolution(sol);
1046 printer->stream(
Debug) <<
"Returning " << sol.
numVecs <<
" eigenpairs to eigenproblem." << std::endl;
1049 numIters_ = lobpcg_solver->getNumIters();
1058 template <
class ScalarType,
class MV,
class OP>
1063 globalTest_ = global;
1066 template <
class ScalarType,
class MV,
class OP>
1067 const Teuchos::RCP< StatusTest<ScalarType,MV,OP> > &
1073 template <
class ScalarType,
class MV,
class OP>
1081 template <
class ScalarType,
class MV,
class OP>
1082 const Teuchos::RCP< StatusTest<ScalarType,MV,OP> > &
1088 template <
class ScalarType,
class MV,
class OP>
1093 lockingTest_ = locking;
1096 template <
class ScalarType,
class MV,
class OP>
1097 const Teuchos::RCP< StatusTest<ScalarType,MV,OP> > &
1100 return lockingTest_;