15#ifndef BELOS_DGKS_ORTHOMANAGER_HPP
16#define BELOS_DGKS_ORTHOMANAGER_HPP
33#include "Teuchos_as.hpp"
34#ifdef BELOS_TEUCHOS_TIME_MONITOR
35#include "Teuchos_TimeMonitor.hpp"
41 template<
class ScalarType,
class MV,
class OP,
class DM = DefaultDenseMatrix<
int,ScalarType>>
45 template<
class ScalarType,
class MV,
class OP,
class DM = DefaultDenseMatrix<
int,ScalarType>>
48 template<
class ScalarType,
class MV,
class OP,
class DM = DefaultDenseMatrix<
int,ScalarType>>
53 typedef typename Teuchos::ScalarTraits<ScalarType>::magnitudeType MagnitudeType;
54 typedef typename Teuchos::ScalarTraits<MagnitudeType> MGT;
55 typedef Teuchos::ScalarTraits<ScalarType> SCT;
66 Teuchos::RCP<const OP> Op = Teuchos::null,
72 max_blk_ortho_( max_blk_ortho ),
75 sing_tol_( sing_tol ),
78#ifdef BELOS_TEUCHOS_TIME_MONITOR
80 ss << label_ +
": DGKS[" << max_blk_ortho_ <<
"]";
82 std::string orthoLabel = ss.str() +
": Orthogonalization";
83 timerOrtho_ = Teuchos::TimeMonitor::getNewCounter(orthoLabel);
85 std::string updateLabel = ss.str() +
": Ortho (Update)";
86 timerUpdate_ = Teuchos::TimeMonitor::getNewCounter(updateLabel);
88 std::string normLabel = ss.str() +
": Ortho (Norm)";
89 timerNorm_ = Teuchos::TimeMonitor::getNewCounter(normLabel);
91 std::string ipLabel = ss.str() +
": Ortho (Inner Product)";
92 timerInnerProd_ = Teuchos::TimeMonitor::getNewCounter(ipLabel);
98 const std::string& label =
"Belos",
99 Teuchos::RCP<const OP> Op = Teuchos::null)
109#ifdef BELOS_TEUCHOS_TIME_MONITOR
110 std::stringstream ss;
111 ss << label_ +
": DGKS[" << max_blk_ortho_ <<
"]";
113 std::string orthoLabel = ss.str() +
": Orthogonalization";
114 timerOrtho_ = Teuchos::TimeMonitor::getNewCounter(orthoLabel);
116 std::string updateLabel = ss.str() +
": Ortho (Update)";
117 timerUpdate_ = Teuchos::TimeMonitor::getNewCounter(updateLabel);
119 std::string normLabel = ss.str() +
": Ortho (Norm)";
120 timerNorm_ = Teuchos::TimeMonitor::getNewCounter(normLabel);
122 std::string ipLabel = ss.str() +
": Ortho (Inner Product)";
123 timerInnerProd_ = Teuchos::TimeMonitor::getNewCounter(ipLabel);
137 using Teuchos::ParameterList;
138 using Teuchos::parameterList;
142 RCP<ParameterList> params;
143 if (plist.is_null()) {
145 params = parameterList (*defaultParams);
148 params->validateParametersAndSetDefaults (*defaultParams);
156 const int maxNumOrthogPasses = params->get<
int> (
"maxNumOrthogPasses");
157 const MagnitudeType blkTol = params->get<MagnitudeType> (
"blkTol");
158 const MagnitudeType depTol = params->get<MagnitudeType> (
"depTol");
159 const MagnitudeType singTol = params->get<MagnitudeType> (
"singTol");
161 max_blk_ortho_ = maxNumOrthogPasses;
166 this->setMyParamList (params);
169 Teuchos::RCP<const Teuchos::ParameterList>
172 if (defaultParams_.is_null()) {
176 return defaultParams_;
187 Teuchos::RCP<Teuchos::ParameterList> params = this->getNonconstParameterList();
188 if (! params.is_null()) {
193 params->set (
"blkTol", blk_tol);
201 Teuchos::RCP<Teuchos::ParameterList> params = this->getNonconstParameterList();
202 if (! params.is_null()) {
203 params->set (
"depTol", dep_tol);
211 Teuchos::RCP<Teuchos::ParameterList> params = this->getNonconstParameterList();
212 if (! params.is_null()) {
213 params->set (
"singTol", sing_tol);
215 sing_tol_ = sing_tol;
261 Teuchos::Array<Teuchos::RCP<DM>> C,
262 Teuchos::ArrayView<Teuchos::RCP<const MV>> Q)
const;
268 Teuchos::Array<Teuchos::RCP<DM>> C,
269 Teuchos::ArrayView<Teuchos::RCP<const MV>> Q)
const {
299 Teuchos::RCP<DM> B)
const;
368 Teuchos::Array<Teuchos::RCP<DM> > C,
370 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const;
382 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
393 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
399 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
408 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
409 orthogError(
const MV &X1, Teuchos::RCP<const MV> MX1,
const MV &X2)
const;
422 const std::string&
getLabel()
const {
return label_; }
454 MagnitudeType blk_tol_;
456 MagnitudeType dep_tol_;
458 MagnitudeType sing_tol_;
462#ifdef BELOS_TEUCHOS_TIME_MONITOR
463 Teuchos::RCP<Teuchos::Time> timerOrtho_, timerUpdate_, timerNorm_, timerInnerProd_;
467 mutable Teuchos::RCP<Teuchos::ParameterList> defaultParams_;
470 int findBasis(MV &X, Teuchos::RCP<MV> MX,
472 bool completeBasis,
int howMany = -1 )
const;
475 bool blkOrtho1 ( MV &X, Teuchos::RCP<MV> MX,
476 Teuchos::Array<Teuchos::RCP<DM>> C,
477 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const;
480 bool blkOrtho ( MV &X, Teuchos::RCP<MV> MX,
481 Teuchos::Array<Teuchos::RCP<DM>> C,
482 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const;
497 int blkOrthoSing ( MV &X, Teuchos::RCP<MV> MX,
498 Teuchos::Array<Teuchos::RCP<DM> > C,
500 Teuchos::ArrayView<Teuchos::RCP<const MV> > QQ)
const;
504 template<
class ScalarType,
class MV,
class OP,
class DM>
507 template<
class ScalarType,
class MV,
class OP,
class DM>
508 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
510 = 10*Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::squareroot(
511 Teuchos::ScalarTraits<
typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::eps() );
513 template<
class ScalarType,
class MV,
class OP,
class DM>
514 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
516 = Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::one()
517 / Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::squareroot(
518 2*Teuchos::ScalarTraits<
typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::one() );
520 template<
class ScalarType,
class MV,
class OP,
class DM>
521 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
523 = 10*Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::eps();
525 template<
class ScalarType,
class MV,
class OP,
class DM>
528 template<
class ScalarType,
class MV,
class OP,
class DM>
529 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
531 = Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::zero();
533 template<
class ScalarType,
class MV,
class OP,
class DM>
534 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
536 = Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::zero();
538 template<
class ScalarType,
class MV,
class OP,
class DM>
539 const typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType
541 = Teuchos::ScalarTraits<typename DGKSOrthoManager<ScalarType,MV,OP,DM>::MagnitudeType>::zero();
545 template<
class ScalarType,
class MV,
class OP,
class DM>
548 if (label != label_) {
550#ifdef BELOS_TEUCHOS_TIME_MONITOR
551 std::stringstream ss;
552 ss << label_ +
": DGKS[" << max_blk_ortho_ <<
"]";
554 std::string orthoLabel = ss.str() +
": Orthogonalization";
555 timerOrtho_ = Teuchos::TimeMonitor::getNewCounter(orthoLabel);
557 std::string updateLabel = ss.str() +
": Ortho (Update)";
558 timerUpdate_ = Teuchos::TimeMonitor::getNewCounter(updateLabel);
560 std::string normLabel = ss.str() +
": Ortho (Norm)";
561 timerNorm_ = Teuchos::TimeMonitor::getNewCounter(normLabel);
563 std::string ipLabel = ss.str() +
": Ortho (Inner Product)";
564 timerInnerProd_ = Teuchos::TimeMonitor::getNewCounter(ipLabel);
571 template<
class ScalarType,
class MV,
class OP,
class DM>
572 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
574 const ScalarType ONE = SCT::one();
578#ifdef BELOS_TEUCHOS_TIME_MONITOR
579 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
584 for (
int i=0; i<rank; i++) {
593 template<
class ScalarType,
class MV,
class OP,
class DM>
594 typename Teuchos::ScalarTraits<ScalarType>::magnitudeType
600#ifdef BELOS_TEUCHOS_TIME_MONITOR
601 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
610 template<
class ScalarType,
class MV,
class OP,
class DM>
615 Teuchos::Array<Teuchos::RCP<DM> > C,
617 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const
619 using Teuchos::Array;
621 using Teuchos::is_null;
624 typedef typename Array< RCP< const MV > >::size_type size_type;
626#ifdef BELOS_TEUCHOS_TIME_MONITOR
627 Teuchos::TimeMonitor orthotimer(*timerOrtho_);
630 ScalarType ONE = SCT::one();
631 const MagnitudeType ZERO = SCT::magnitude(SCT::zero());
652 for (size_type k = 0; k < nq; ++k)
655 const int numCols = xc;
667 if (MX == Teuchos::null) {
675 MX = Teuchos::rcp( &X,
false );
682 TEUCHOS_TEST_FOR_EXCEPTION( xc == 0 || xr == 0, std::invalid_argument,
"Belos::DGKSOrthoManager::projectAndNormalize(): X must be non-empty" );
685 for (
int i=0; i<nq; i++) {
691 "Belos::DGKSOrthoManager::projectAndNormalize(): Size of X must be consistant with size of B" );
693 TEUCHOS_TEST_FOR_EXCEPTION( xc<0 || xr<0 || mxc<0 || mxr<0, std::invalid_argument,
694 "Belos::DGKSOrthoManager::projectAndNormalize(): MVT returned negative dimensions for X,MX" );
696 TEUCHOS_TEST_FOR_EXCEPTION( xc!=mxc || xr!=mxr, std::invalid_argument,
697 "Belos::DGKSOrthoManager::projectAndNormalize(): Size of X must be consistant with size of MX" );
703 bool dep_flg =
false;
709 dep_flg = blkOrtho1( X, MX, C, Q );
712 if ( B == Teuchos::null ) {
715 std::vector<ScalarType> dot(1);
717#ifdef BELOS_TEUCHOS_TIME_MONITOR
718 Teuchos::TimeMonitor normTimer( *timerNorm_ );
723 ScalarType diag = SCT::squareroot(SCT::magnitude(dot[0]));
727 if (SCT::magnitude(diag) > ZERO) {
739 Teuchos::RCP<MV> tmpX, tmpMX;
746 dep_flg = blkOrtho( X, MX, C, Q );
751 rank = blkOrthoSing( *tmpX, tmpMX, C, B, Q );
761 rank = findBasis( X, MX, B,
false );
765 rank = blkOrthoSing( *tmpX, tmpMX, C, B, Q );
777 TEUCHOS_TEST_FOR_EXCEPTION( rank > xc || rank < 0, std::logic_error,
778 "Belos::DGKSOrthoManager::projectAndNormalize(): Debug error in rank variable." );
788 template<
class ScalarType,
class MV,
class OP,
class DM>
790 MV &X, Teuchos::RCP<MV> MX,
791 Teuchos::RCP<DM> B )
const {
793#ifdef BELOS_TEUCHOS_TIME_MONITOR
794 Teuchos::TimeMonitor orthotimer(*timerOrtho_);
798 return findBasis(X, MX, B,
true);
805 template<
class ScalarType,
class MV,
class OP,
class DM>
807 MV &X, Teuchos::RCP<MV> MX,
808 Teuchos::Array<Teuchos::RCP<DM> > C,
809 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const {
825#ifdef BELOS_TEUCHOS_TIME_MONITOR
826 Teuchos::TimeMonitor orthotimer(*timerOrtho_);
832 std::vector<int> qcs(nq);
834 if (nq == 0 || xc == 0 || xr == 0) {
846 if (MX == Teuchos::null) {
854 MX = Teuchos::rcp( &X,
false );
860 TEUCHOS_TEST_FOR_EXCEPTION( xc<0 || xr<0 || mxc<0 || mxr<0, std::invalid_argument,
861 "Belos::DGKSOrthoManager::project(): MVT returned negative dimensions for X,MX" );
863 TEUCHOS_TEST_FOR_EXCEPTION( xc!=mxc || xr!=mxr || xr!=qr, std::invalid_argument,
864 "Belos::DGKSOrthoManager::project(): Size of X not consistant with MX,Q" );
867 for (
int i=0; i<nq; i++) {
869 "Belos::DGKSOrthoManager::project(): Q lengths not mutually consistant" );
871 TEUCHOS_TEST_FOR_EXCEPTION( qr < qcs[i], std::invalid_argument,
872 "Belos::DGKSOrthoManager::project(): Q has less rows than columns" );
875 if ( C[i] == Teuchos::null ) {
880 "Belos::DGKSOrthoManager::project(): Size of Q not consistant with size of C" );
885 blkOrtho( X, MX, C, Q );
892 template<
class ScalarType,
class MV,
class OP,
class DM>
893 int DGKSOrthoManager<ScalarType, MV, OP, DM>::findBasis( MV &X, Teuchos::RCP<MV> MX,
895 bool completeBasis,
int howMany )
const {
912 const ScalarType ONE = SCT::one();
913 const MagnitudeType ZERO = SCT::magnitude(SCT::zero());
915 int xc = MVT::GetNumberVecs( X );
916 ptrdiff_t xr = MVT::GetGlobalLength( X );
929 if (MX == Teuchos::null) {
931 MX = MVT::Clone(X,xc);
932 OPT::Apply(*(this->_Op),X,*MX);
939 if ( B == Teuchos::null ) {
940 B = DMT::Create(xc,xc);
943 int mxc = (this->_hasOp) ? MVT::GetNumberVecs( *MX ) : xc;
944 ptrdiff_t mxr = (this->_hasOp) ? MVT::GetGlobalLength( *MX ) : xr;
947 TEUCHOS_TEST_FOR_EXCEPTION( xc == 0 || xr == 0, std::invalid_argument,
948 "Belos::DGKSOrthoManager::findBasis(): X must be non-empty" );
949 TEUCHOS_TEST_FOR_EXCEPTION( DMT::GetNumRows(*B) != xc || DMT::GetNumCols(*B) != xc, std::invalid_argument,
950 "Belos::DGKSOrthoManager::findBasis(): Size of X not consistant with size of B" );
951 TEUCHOS_TEST_FOR_EXCEPTION( xc != mxc || xr != mxr, std::invalid_argument,
952 "Belos::DGKSOrthoManager::findBasis(): Size of X not consistant with size of MX" );
953 TEUCHOS_TEST_FOR_EXCEPTION(
static_cast<ptrdiff_t
>(xc) > xr, std::invalid_argument,
954 "Belos::DGKSOrthoManager::findBasis(): Size of X not feasible for normalization" );
955 TEUCHOS_TEST_FOR_EXCEPTION( howMany < 0 || howMany > xc, std::invalid_argument,
956 "Belos::DGKSOrthoManager::findBasis(): Invalid howMany parameter" );
961 int xstart = xc - howMany;
963 for (
int j = xstart; j < xc; j++) {
972 std::vector<int> index(1);
974 Teuchos::RCP<MV> Xj = MVT::CloneViewNonConst( X, index );
975 Teuchos::RCP<MV> MXj;
976 if ((this->_hasOp)) {
978 MXj = MVT::CloneViewNonConst( *MX, index );
986 std::vector<int> prev_idx( numX );
987 Teuchos::RCP<const MV> prevX, prevMX;
988 Teuchos::RCP<MV> oldMXj;
991 for (
int i=0; i<numX; i++) {
994 prevX = MVT::CloneView( X, prev_idx );
996 prevMX = MVT::CloneView( *MX, prev_idx );
999 oldMXj = MVT::CloneCopy( *MXj );
1003 Teuchos::RCP<DM> product = DMT::Create(numX,1);
1004 std::vector<ScalarType> oldDot( 1 ), newDot( 1 );
1009#ifdef BELOS_TEUCHOS_TIME_MONITOR
1010 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1012 MVT::MvDot( *Xj, *MXj, oldDot );
1015 TEUCHOS_TEST_FOR_EXCEPTION( SCT::real(oldDot[0]) < ZERO,
OrthoError,
1016 "Belos::DGKSOrthoManager::findBasis(): Negative definiteness discovered in inner product" );
1023#ifdef BELOS_TEUCHOS_TIME_MONITOR
1024 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1031#ifdef BELOS_TEUCHOS_TIME_MONITOR
1032 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1034 MVT::MvTimesMatAddMv( -ONE, *prevX, *product, ONE, *Xj );
1042#ifdef BELOS_TEUCHOS_TIME_MONITOR
1043 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1045 MVT::MvTimesMatAddMv( -ONE, *prevMX, *product, ONE, *MXj );
1050#ifdef BELOS_TEUCHOS_TIME_MONITOR
1051 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1053 MVT::MvDot( *Xj, *MXj, newDot );
1057 if ( MGT::squareroot(SCT::magnitude(newDot[0])) < dep_tol_*MGT::squareroot(SCT::magnitude(oldDot[0])) ) {
1060 Teuchos::RCP<DM> P2 = DMT::Create(numX,1);
1062#ifdef BELOS_TEUCHOS_TIME_MONITOR
1063 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1067 DMT::Add(*product,*P2);
1070#ifdef BELOS_TEUCHOS_TIME_MONITOR
1071 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1073 MVT::MvTimesMatAddMv( -ONE, *prevX, *P2, ONE, *Xj );
1075 if ((this->_hasOp)) {
1076#ifdef BELOS_TEUCHOS_TIME_MONITOR
1077 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1079 MVT::MvTimesMatAddMv( -ONE, *prevMX, *P2, ONE, *MXj );
1087#ifdef BELOS_TEUCHOS_TIME_MONITOR
1088 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1090 MVT::MvDot( *Xj, *oldMXj, newDot );
1093 newDot[0] = oldDot[0];
1097 if (completeBasis) {
1101 if ( SCT::magnitude(newDot[0]) < SCT::magnitude(sing_tol_*oldDot[0]) ) {
1106 std::cout <<
"Belos::DGKSOrthoManager::findBasis() --> Random for column " << numX << std::endl;
1109 Teuchos::RCP<MV> tempXj = MVT::Clone( X, 1 );
1110 Teuchos::RCP<MV> tempMXj;
1111 MVT::MvRandom( *tempXj );
1113 tempMXj = MVT::Clone( X, 1 );
1114 OPT::Apply( *(this->_Op), *tempXj, *tempMXj );
1120#ifdef BELOS_TEUCHOS_TIME_MONITOR
1121 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1123 MVT::MvDot( *tempXj, *tempMXj, oldDot );
1126 for (
int num_orth=0; num_orth<max_blk_ortho_; num_orth++){
1128#ifdef BELOS_TEUCHOS_TIME_MONITOR
1129 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1134#ifdef BELOS_TEUCHOS_TIME_MONITOR
1135 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1137 MVT::MvTimesMatAddMv( -ONE, *prevX, *product, ONE, *tempXj );
1140#ifdef BELOS_TEUCHOS_TIME_MONITOR
1141 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1143 MVT::MvTimesMatAddMv( -ONE, *prevMX, *product, ONE, *tempMXj );
1148#ifdef BELOS_TEUCHOS_TIME_MONITOR
1149 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1151 MVT::MvDot( *tempXj, *tempMXj, newDot );
1154 if ( SCT::magnitude(newDot[0]) >= SCT::magnitude(oldDot[0]*sing_tol_) ) {
1156 MVT::Assign( *tempXj, *Xj );
1158 MVT::Assign( *tempMXj, *MXj );
1170 if ( SCT::magnitude(newDot[0]) < SCT::magnitude(oldDot[0]*blk_tol_) ) {
1178 ScalarType diag = SCT::squareroot(SCT::magnitude(newDot[0]));
1180 if (SCT::magnitude(diag) > ZERO) {
1181 MVT::MvScale( *Xj, ONE/diag );
1184 MVT::MvScale( *MXj, ONE/diag );
1189 Teuchos::RCP<DM> Bjj = DMT::Subview(*B,1,1,j,j);
1191 DMT::PutScalar(*Bjj, ZERO);
1194 DMT::PutScalar(*Bjj, diag);
1199 Teuchos::RCP<DM> Bcolj = DMT::Subview(*B,numX,1,0,j);
1200 DMT::Assign(*Bcolj,*product);
1209 template<
class ScalarType,
class MV,
class OP,
class DM>
1211 DGKSOrthoManager<ScalarType, MV, OP, DM>::blkOrtho1 ( MV &X, Teuchos::RCP<MV> MX,
1212 Teuchos::Array<Teuchos::RCP<DM> > C,
1213 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const
1216 int xc = MVT::GetNumberVecs( X );
1217 const ScalarType ONE = SCT::one();
1219 std::vector<int> qcs( nq );
1220 for (
int i=0; i<nq; i++) {
1221 qcs[i] = MVT::GetNumberVecs( *Q[i] );
1225 std::vector<ScalarType> oldDot( 1 ), newDot( 1 );
1227#ifdef BELOS_TEUCHOS_TIME_MONITOR
1228 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1230 MVT::MvDot( X, *MX, oldDot );
1233 Teuchos::Array<Teuchos::RCP<MV> > MQ(nq);
1235 for (
int i=0; i<nq; i++) {
1238#ifdef BELOS_TEUCHOS_TIME_MONITOR
1239 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1245#ifdef BELOS_TEUCHOS_TIME_MONITOR
1246 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1248 MVT::MvTimesMatAddMv( -ONE, *Q[i], *C[i], ONE, X );
1254 OPT::Apply( *(this->_Op), X, *MX);
1258 MQ[i] = MVT::Clone( *Q[i], qcs[i] );
1259 OPT::Apply( *(this->_Op), *Q[i], *MQ[i] );
1261#ifdef BELOS_TEUCHOS_TIME_MONITOR
1262 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1264 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *C[i], ONE, *MX );
1271#ifdef BELOS_TEUCHOS_TIME_MONITOR
1272 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1274 MVT::MvDot( X, *MX, newDot );
1288 if ( MGT::squareroot(SCT::magnitude(newDot[0])) < dep_tol_*MGT::squareroot(SCT::magnitude(oldDot[0])) ) {
1291 for (
int i=0; i<nq; i++) {
1292 Teuchos::RCP<DM> C2 = DMT::Create(DMT::GetNumRows(*C[i]),DMT::GetNumCols(*C[i]));
1296#ifdef BELOS_TEUCHOS_TIME_MONITOR
1297 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1301 DMT::Add(*C[i],*C2);
1304#ifdef BELOS_TEUCHOS_TIME_MONITOR
1305 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1307 MVT::MvTimesMatAddMv( -ONE, *Q[i], *C2, ONE, X );
1313#ifdef BELOS_TEUCHOS_TIME_MONITOR
1314 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1317 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *C2, ONE, *MX );
1319 else if (xc <= qcs[i]) {
1321 OPT::Apply( *(this->_Op), X, *MX);
1332 template<
class ScalarType,
class MV,
class OP,
class DM>
1334 DGKSOrthoManager<ScalarType, MV, OP, DM>::blkOrtho ( MV &X, Teuchos::RCP<MV> MX,
1335 Teuchos::Array<Teuchos::RCP<DM> > C,
1336 Teuchos::ArrayView<Teuchos::RCP<const MV> > Q)
const
1339 int xc = MVT::GetNumberVecs( X );
1340 bool dep_flg =
false;
1341 const ScalarType ONE = SCT::one();
1343 std::vector<int> qcs( nq );
1344 for (
int i=0; i<nq; i++) {
1345 qcs[i] = MVT::GetNumberVecs( *Q[i] );
1351 std::vector<ScalarType> oldDot( xc );
1353#ifdef BELOS_TEUCHOS_TIME_MONITOR
1354 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1356 MVT::MvDot( X, *MX, oldDot );
1359 Teuchos::Array<Teuchos::RCP<MV> > MQ(nq);
1361 for (
int i=0; i<nq; i++) {
1364#ifdef BELOS_TEUCHOS_TIME_MONITOR
1365 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1371#ifdef BELOS_TEUCHOS_TIME_MONITOR
1372 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1374 MVT::MvTimesMatAddMv( -ONE, *Q[i], *C[i], ONE, X );
1380 OPT::Apply( *(this->_Op), X, *MX);
1384 MQ[i] = MVT::Clone( *Q[i], qcs[i] );
1385 OPT::Apply( *(this->_Op), *Q[i], *MQ[i] );
1387#ifdef BELOS_TEUCHOS_TIME_MONITOR
1388 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1390 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *C[i], ONE, *MX );
1397 for (
int j = 1; j < max_blk_ortho_; ++j) {
1399 for (
int i=0; i<nq; i++) {
1400 Teuchos::RCP<DM> C2 = DMT::Create(DMT::GetNumRows(*C[i]),DMT::GetNumCols(*C[i]));
1404#ifdef BELOS_TEUCHOS_TIME_MONITOR
1405 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1409 DMT::Add(*C[i],*C2);
1412#ifdef BELOS_TEUCHOS_TIME_MONITOR
1413 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1415 MVT::MvTimesMatAddMv( -ONE, *Q[i], *C2, ONE, X );
1421#ifdef BELOS_TEUCHOS_TIME_MONITOR
1422 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1425 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *C2, ONE, *MX );
1427 else if (xc <= qcs[i]) {
1429 OPT::Apply( *(this->_Op), X, *MX);
1436 std::vector<ScalarType> newDot(xc);
1438#ifdef BELOS_TEUCHOS_TIME_MONITOR
1439 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1441 MVT::MvDot( X, *MX, newDot );
1445 for (
int i=0; i<xc; i++){
1446 if (SCT::magnitude(newDot[i]) < SCT::magnitude(oldDot[i] * blk_tol_)) {
1456 template<
class ScalarType,
class MV,
class OP,
class DM>
1458 DGKSOrthoManager<ScalarType, MV, OP, DM>::blkOrthoSing ( MV &X, Teuchos::RCP<MV> MX,
1459 Teuchos::Array<Teuchos::RCP<DM> > C,
1461 Teuchos::ArrayView<Teuchos::RCP<const MV> > QQ)
const
1463 Teuchos::Array<Teuchos::RCP<const MV> > Q (QQ);
1465 const ScalarType ONE = SCT::one();
1466 const ScalarType ZERO = SCT::zero();
1469 int xc = MVT::GetNumberVecs( X );
1470 std::vector<int> indX( 1 );
1471 std::vector<ScalarType> oldDot( 1 ), newDot( 1 );
1473 std::vector<int> qcs( nq );
1474 for (
int i=0; i<nq; i++) {
1475 qcs[i] = MVT::GetNumberVecs( *Q[i] );
1479 Teuchos::RCP<const MV> lastQ;
1480 Teuchos::RCP<MV> Xj, MXj;
1481 Teuchos::RCP<DM> lastC = DMT::Create();
1484 for (
int j=0; j<xc; j++) {
1486 bool dep_flg =
false;
1490 std::vector<int> index( j );
1491 for (
int ind=0; ind<j; ind++) {
1494 lastQ = MVT::CloneView( X, index );
1497 Q.push_back( lastQ );
1499 qcs.push_back( MVT::GetNumberVecs( *lastQ ) );
1504 Xj = MVT::CloneViewNonConst( X, indX );
1506 MXj = MVT::CloneViewNonConst( *MX, indX );
1514#ifdef BELOS_TEUCHOS_TIME_MONITOR
1515 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1517 MVT::MvDot( *Xj, *MXj, oldDot );
1520 Teuchos::Array<Teuchos::RCP<MV> > MQ(Q.size());
1522 for (
int i=0; i<Q.size(); i++) {
1525 Teuchos::RCP<DM> tempC = DMT::Subview(*C[i], qcs[i], 1, 0, j);
1529#ifdef BELOS_TEUCHOS_TIME_MONITOR
1530 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1536#ifdef BELOS_TEUCHOS_TIME_MONITOR
1537 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1539 MVT::MvTimesMatAddMv( -ONE, *Q[i], *tempC, ONE, *Xj );
1545 OPT::Apply( *(this->_Op), *Xj, *MXj);
1549 MQ[i] = MVT::Clone( *Q[i], qcs[i] );
1550 OPT::Apply( *(this->_Op), *Q[i], *MQ[i] );
1552#ifdef BELOS_TEUCHOS_TIME_MONITOR
1553 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1555 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *tempC, ONE, *MXj );
1563#ifdef BELOS_TEUCHOS_TIME_MONITOR
1564 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1566 MVT::MvDot( *Xj, *MXj, newDot );
1572 if ( SCT::magnitude(newDot[0]) < SCT::magnitude(oldDot[0]*dep_tol_) ) {
1574 for (
int i=0; i<Q.size(); i++) {
1575 Teuchos::RCP<DM> tempC = DMT::Subview(*C[i], qcs[i], 1, 0, j);
1576 Teuchos::RCP<DM> C2 = DMT::Create(qcs[i],1);
1580#ifdef BELOS_TEUCHOS_TIME_MONITOR
1581 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1585 DMT::Add(*tempC,*C2);
1587#ifdef BELOS_TEUCHOS_TIME_MONITOR
1588 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1590 MVT::MvTimesMatAddMv( -ONE, *Q[i], *C2, ONE, *Xj );
1596#ifdef BELOS_TEUCHOS_TIME_MONITOR
1597 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1600 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *C2, ONE, *MXj );
1602 else if (xc <= qcs[i]) {
1604 OPT::Apply( *(this->_Op), *Xj, *MXj);
1611#ifdef BELOS_TEUCHOS_TIME_MONITOR
1612 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1614 MVT::MvDot( *Xj, *MXj, newDot );
1619 if (SCT::magnitude(newDot[0]) < SCT::magnitude(oldDot[0]*sing_tol_)) {
1625 ScalarType diag = SCT::squareroot(SCT::magnitude(newDot[0]));
1627 MVT::MvScale( *Xj, ONE/diag );
1630 MVT::MvScale( *MXj, ONE/diag );
1634 Teuchos::RCP<DM> Bjj = DMT::Subview(*B,1,1,j,j);
1635 DMT::PutScalar(*Bjj, diag);
1639 Teuchos::RCP<MV> tempXj = MVT::Clone( X, 1 );
1640 Teuchos::RCP<MV> tempMXj;
1641 MVT::MvRandom( *tempXj );
1643 tempMXj = MVT::Clone( X, 1 );
1644 OPT::Apply( *(this->_Op), *tempXj, *tempMXj );
1650#ifdef BELOS_TEUCHOS_TIME_MONITOR
1651 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1653 MVT::MvDot( *tempXj, *tempMXj, oldDot );
1656 for (
int num_orth=0; num_orth<max_blk_ortho_; num_orth++) {
1658 for (
int i=0; i<Q.size(); i++) {
1659 Teuchos::RCP<DM> product = DMT::Create( qcs[i], 1 );
1663#ifdef BELOS_TEUCHOS_TIME_MONITOR
1664 Teuchos::TimeMonitor innerProdTimer( *timerInnerProd_ );
1669#ifdef BELOS_TEUCHOS_TIME_MONITOR
1670 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1672 MVT::MvTimesMatAddMv( -ONE, *Q[i], *product, ONE, *tempXj );
1678#ifdef BELOS_TEUCHOS_TIME_MONITOR
1679 Teuchos::TimeMonitor updateTimer( *timerUpdate_ );
1682 MVT::MvTimesMatAddMv( -ONE, *MQ[i], *product, ONE, *tempMXj );
1684 else if (xc <= qcs[i]) {
1686 OPT::Apply( *(this->_Op), *tempXj, *tempMXj);
1695#ifdef BELOS_TEUCHOS_TIME_MONITOR
1696 Teuchos::TimeMonitor normTimer( *timerNorm_ );
1698 MVT::MvDot( *tempXj, *tempMXj, newDot );
1702 if ( SCT::magnitude(newDot[0]) >= SCT::magnitude(oldDot[0]*sing_tol_) ) {
1703 ScalarType diag = SCT::squareroot(SCT::magnitude(newDot[0]));
1706 Teuchos::RCP<DM> Bjj = DMT::Subview(*B,1,1,j,j);
1707 DMT::PutScalar(*Bjj, ZERO);
1710 MVT::MvAddMv( ONE/diag, *tempXj, ZERO, *tempXj, *Xj );
1712 MVT::MvAddMv( ONE/diag, *tempMXj, ZERO, *tempMXj, *MXj );
1732 template<
class ScalarType,
class MV,
class OP,
class DM>
1735 using Teuchos::ParameterList;
1736 using Teuchos::parameterList;
1739 RCP<ParameterList> params = parameterList (
"DGKS");
1744 "Maximum number of orthogonalization passes (includes the "
1745 "first). Default is 2, since \"twice is enough\" for Krylov "
1748 "Block reorthogonalization threshold.");
1750 "(Non-block) reorthogonalization threshold.");
1752 "Singular block detection threshold.");
1757 template<
class ScalarType,
class MV,
class OP,
class DM>
1760 using Teuchos::ParameterList;
1765 params->set (
"maxNumOrthogPasses",
1767 params->set (
"blkTol",
1769 params->set (
"depTol",
1771 params->set (
"singTol",
1779#ifdef HAVE_BELOS_TPETRA
1782#define BELOS_TPETRA_DGKSORTHOMANAGER_NOEXTERN_CALL(SC, LO, GO, NT) \
1783 BELOS_TPETRA_CALL(Belos::DGKSOrthoManager, SC, LO, GO, NT)
1785#define BELOS_TPETRA_DGKSORTHOMANAGER_EXTERN_CALL(SC, LO, GO, NT) \
1786 BELOS_TPETRA_EXTERN_CALL(Belos::DGKSOrthoManager, SC, LO, GO, NT)
1788TPETRA_INSTANTIATE_SLGN_NO_ORDINAL_SCALAR(BELOS_TPETRA_DGKSORTHOMANAGER_EXTERN_CALL)
Belos header file which uses auto-configuration information to include necessary C++ headers.
Templated virtual class for providing orthogonalization/orthonormalization methods with matrix-based ...
Declaration of basic traits for the multivector type.
Class which defines basic traits for the operator type.
static const MagnitudeType blk_tol_default_
static const MagnitudeType sing_tol_default_
int normalize(MV &X, Teuchos::RCP< DM > B) const
This method calls normalize(X,Teuchos::null,B); see documentation for that function.
static const MagnitudeType dep_tol_fast_
static const MagnitudeType dep_tol_default_
void setParameterList(const Teuchos::RCP< Teuchos::ParameterList > &plist)
virtual int projectAndNormalizeWithMxImpl(MV &X, Teuchos::RCP< MV > MX, Teuchos::Array< Teuchos::RCP< DM > > C, Teuchos::RCP< DM > B, Teuchos::ArrayView< Teuchos::RCP< const MV > > Q) const
Given a set of bases Q[i] and a multivector X, this method computes an orthonormal basis for .
static const int max_blk_ortho_default_
Teuchos::ScalarTraits< ScalarType >::magnitudeType orthogError(const MV &X1, const MV &X2) const
This method computes the error in orthogonality of two multivectors, measured as the Frobenius norm o...
int normalize(MV &X, Teuchos::RCP< MV > MX, Teuchos::RCP< DM > B) const
This method takes a multivector X and attempts to compute an orthonormal basis for ,...
void project(MV &X, Teuchos::RCP< MV > MX, Teuchos::Array< Teuchos::RCP< DM > > C, Teuchos::ArrayView< Teuchos::RCP< const MV > > Q) const
Given a list of (mutually and internally) orthonormal bases Q, this method takes a multivector X and ...
static const int max_blk_ortho_fast_
MagnitudeType getBlkTol() const
Return parameter for block re-orthogonalization threshhold.
void setLabel(const std::string &label)
This method sets the label used by the timers in the orthogonalization manager.
Teuchos::ScalarTraits< ScalarType >::magnitudeType orthonormError(const MV &X, Teuchos::RCP< const MV > MX) const
This method computes the error in orthonormality of a multivector. The method has the option of explo...
void setBlkTol(const MagnitudeType blk_tol)
Set parameter for block re-orthogonalization threshhold.
static const MagnitudeType blk_tol_fast_
MagnitudeType getDepTol() const
Return parameter for re-orthogonalization threshhold.
~DGKSOrthoManager()
Destructor.
void project(MV &X, Teuchos::Array< Teuchos::RCP< DM > > C, Teuchos::ArrayView< Teuchos::RCP< const MV > > Q) const
This method calls project(X,Teuchos::null,C,Q); see documentation for that function.
Teuchos::ScalarTraits< ScalarType >::magnitudeType orthonormError(const MV &X) const
This method computes the error in orthonormality of a multivector.
Teuchos::ScalarTraits< ScalarType >::magnitudeType orthogError(const MV &X1, Teuchos::RCP< const MV > MX1, const MV &X2) const
This method computes the error in orthogonality of two multivectors, measured as the Frobenius norm o...
static const MagnitudeType sing_tol_fast_
DGKSOrthoManager(const std::string &label="Belos", Teuchos::RCP< const OP > Op=Teuchos::null, const int max_blk_ortho=max_blk_ortho_default_, const MagnitudeType blk_tol=blk_tol_default_, const MagnitudeType dep_tol=dep_tol_default_, const MagnitudeType sing_tol=sing_tol_default_)
Constructor specifying re-orthogonalization tolerance.
void setSingTol(const MagnitudeType sing_tol)
Set parameter for singular block detection.
const std::string & getLabel() const
This method returns the label being used by the timers in the orthogonalization manager.
MagnitudeType getSingTol() const
Return parameter for singular block detection.
DGKSOrthoManager(const Teuchos::RCP< Teuchos::ParameterList > &plist, const std::string &label="Belos", Teuchos::RCP< const OP > Op=Teuchos::null)
Constructor that takes a list of parameters.
void setDepTol(const MagnitudeType dep_tol)
Set parameter for re-orthogonalization threshhold.
Teuchos::RCP< const Teuchos::ParameterList > getValidParameters() const
Virtual base class which defines basic traits for the multi-vector type.
static Teuchos::RCP< DM > Subview(DM &source, int numRows, int numCols, int startRow=0, int startCol=0)
Marks host data modified to avoid device sync errors.
static void SyncHostToDevice(DM &dm)
static void PutScalar(DM &dm, ScalarType value=Teuchos::ScalarTraits< ScalarType >::zero())
Fill all entries with value. Value is zero if not specified.
static int GetNumRows(const DM &dm)
Obtain the number of rows of dm.
static void SyncDeviceToHost(DM &dm)
static void Reshape(DM &dm, const int numrows, const int numcols, bool initZero=false)
static ScalarType & Value(DM &dm, const int i, const int j)
Access a reference to the (i,j) entry of dm, e_i^T dm e_j.
static Teuchos::ScalarTraits< ScalarType >::magnitudeType NormFrobenius(const DM &dm)
Returns the Frobenius norm of the dense matrix.
static Teuchos::RCP< DM > Create()
Creates a new empty DM with no dimension.
static int GetNumCols(const DM &dm)
Obtain the number of columns of dm.
void innerProd(const MV &X, const MV &Y, DM &Z) const
Provides the inner product defining the orthogonality concepts, using the provided operator.
MatOrthoManager(Teuchos::RCP< const OP > Op=Teuchos::null)
Default constructor.
Teuchos::RCP< const OP > _Op
Traits class which defines basic operations on multivectors.
static Teuchos::RCP< MV > CloneCopy(const MV &mv)
static Teuchos::RCP< MV > Clone(const MV &mv, const int numvecs)
static void Assign(const MV &A, MV &mv)
static ptrdiff_t GetGlobalLength(const MV &mv)
static void MvDot(const MV &mv, const MV &A, std::vector< ScalarType > &b)
static void MvScale(MV &mv, const ScalarType alpha)
static int GetNumberVecs(const MV &mv)
Class which defines basic traits for the operator type.
static void Apply(const OP &Op, const MV &x, MV &y, ETrans trans=NOTRANS)
Apply Op to x, putting the result into y.
Exception thrown to signal error in an orthogonalization manager method.
Teuchos::RCP< Teuchos::ParameterList > getDGKSDefaultParameters()
"Default" parameters for robustness and accuracy.
Teuchos::RCP< Teuchos::ParameterList > getDGKSFastParameters()
"Fast" but possibly unsafe or less accurate parameters.