10#ifndef THYRA_DEFAULT_ADDED_LINEAR_OP_DEF_HPP 
   11#define THYRA_DEFAULT_ADDED_LINEAR_OP_DEF_HPP 
   13#include "Thyra_DefaultAddedLinearOp_decl.hpp" 
   14#include "Thyra_DefaultScaledAdjointLinearOp.hpp" 
   15#include "Thyra_AssertOp.hpp" 
   16#include "Teuchos_Utils.hpp" 
   27void DefaultAddedLinearOp<Scalar>::assertInitialized()
 const 
   37std::string DefaultAddedLinearOp<Scalar>::getClassName()
 const 
   45Ordinal DefaultAddedLinearOp<Scalar>::getRangeDim()
 const 
   47  return (numOps() > 0 ? this->range()->dim() : 0);
 
   53Ordinal DefaultAddedLinearOp<Scalar>::getDomainDim()
 const 
   55  return (numOps() > 0 ? this->domain()->dim() : 0);
 
   87  const int l_numOps = Ops.size();
 
   88  Ops_.resize(l_numOps);
 
   89  for( 
int k = 0; k < l_numOps; ++k )
 
   90    Ops_[k].initialize(Ops[k]);
 
   92  setupDefaultObjectLabel();
 
 
  100  const int l_numOps = Ops.size();
 
  101  Ops_.resize(l_numOps);
 
  102  for( 
int k = 0; k < l_numOps; ++k )
 
  103    Ops_[k].initialize(Ops[k]);
 
  105  setupDefaultObjectLabel();
 
 
  109template<
class Scalar>
 
  113  setupDefaultObjectLabel();
 
 
  120template<
class Scalar>
 
  127template<
class Scalar>
 
  133  return Ops_[k].isConst();
 
 
  137template<
class Scalar>
 
  144  return Ops_[k].getNonconstObj();
 
 
  148template<
class Scalar>
 
  162template<
class Scalar>
 
  167    return getOp(0)->range();
 
 
  173template<
class Scalar>
 
  178    return getOp(numOps()-1)->domain();
 
 
  184template<
class Scalar>
 
  195template<
class Scalar>
 
  198  std::ostringstream oss;
 
  199  oss << getClassName() << 
"{numOps="<<numOps()
 
  200      <<
",rangeDim=" << getRangeDim()
 
  201      << 
",domainDim="<< getDomainDim() <<
"}";
 
 
  206template<
class Scalar>
 
  217  const int l_numOps = Ops_.size();
 
  221      *out << this->description() << std::endl;
 
  227      *out << this->description() << std::endl;
 
  230         <<  
"Constituent LinearOpBase objects for M = Op[0]*...*Op[numOps-1]:\n";
 
  232      for( 
int k = 0; k < l_numOps; ++k ) {
 
  233        *out << 
"Op["<<k<<
"] = " << Teuchos::describe(*getOp(k),verbLevel);
 
 
  249template<
class Scalar>
 
  252  bool isOpSupported = 
true;
 
  253  for( 
int k = 0; k < static_cast<int>(Ops_.size()); ++k )
 
  254    if(!Thyra::opSupported(*getOp(k),M_trans)) isOpSupported = 
false;
 
  255  return isOpSupported;
 
 
  260template<
class Scalar>
 
  272    getClassName()+
"::apply(...)", *
this, M_trans, X, &*Y
 
  282  const int l_numOps = Ops_.size();
 
  283  for( 
int j = 0; j < l_numOps; ++j )
 
  284    Thyra::apply(*getOp(j), M_trans, X, Y, alpha, j==0 ? beta : ST::one());
 
 
  291template<
class Scalar>
 
  297    const int l_numOps = Ops_.size();
 
  298    for( 
int k = 0; k < l_numOps; ++k ) {
 
  302          getClassName()+
"::initialize(...)" 
  317template<
class Scalar>
 
  318void DefaultAddedLinearOp<Scalar>::setupDefaultObjectLabel()
 
  320  std::ostringstream label;
 
  321  const int l_numOps = Ops_.size();
 
  322  for( 
int k = 0; k < l_numOps; ++k ) {
 
  323    std::string Op_k_label = Ops_[k]->getObjectLabel();
 
  324    if (Op_k_label.length() == 0)
 
  328    label << 
"("<<Op_k_label<<
")";
 
  330  this->setObjectLabel(label.str());
 
  338template<
class Scalar>
 
  341  const RCP<LinearOpBase<Scalar> > &A,
 
  342  const RCP<LinearOpBase<Scalar> > &B,
 
  343  const std::string &label
 
  346  using Teuchos::tuple;
 
  347  RCP<LinearOpBase<Scalar> > alo =
 
  348    defaultAddedLinearOp<Scalar>(
 
  349      tuple<RCP<LinearOpBase<Scalar> > >(A, B)()
 
  352    alo->setObjectLabel(label);
 
  357template<
class Scalar>
 
  360  const RCP<
const LinearOpBase<Scalar> > &A,
 
  361  const RCP<
const LinearOpBase<Scalar> > &B,
 
  362  const std::string &label
 
  365  using Teuchos::tuple;
 
  366  RCP<LinearOpBase<Scalar> > alo =
 
  367    defaultAddedLinearOp<Scalar>(
 
  368      tuple<RCP<
const LinearOpBase<Scalar> > >(A, B)()
 
  371    alo->setObjectLabel(label);
 
  376template<
class Scalar>
 
  378Thyra::nonconstSubtract(
 
  379  const RCP<LinearOpBase<Scalar> > &A,
 
  380  const RCP<LinearOpBase<Scalar> > &B,
 
  381  const std::string &label
 
  384  typedef ScalarTraits<Scalar> ST;
 
  385  using Teuchos::tuple;
 
  386  RCP<LinearOpBase<Scalar> > alo =
 
  387    defaultAddedLinearOp<Scalar>(
 
  388      tuple<RCP<LinearOpBase<Scalar> > >(
 
  389        A, nonconstScale<Scalar>(-ST::one(),B) )()
 
  392    alo->setObjectLabel(label);
 
  397template<
class Scalar>
 
  400  const RCP<
const LinearOpBase<Scalar> > &A,
 
  401  const RCP<
const LinearOpBase<Scalar> > &B,
 
  402  const std::string &label
 
  405  typedef ScalarTraits<Scalar> ST;
 
  406  using Teuchos::tuple;
 
  407  RCP<LinearOpBase<Scalar> > alo =
 
  408    defaultAddedLinearOp<Scalar>(
 
  409      tuple<RCP<
const LinearOpBase<Scalar> > >(
 
  410          A, scale<Scalar>(-ST::one(),B)
 
  414    alo->setObjectLabel(label);
 
  423#define THYRA_DEFAULT_ADDED_LINEAR_OP_INSTANT(SCALAR) \ 
  424  template class DefaultAddedLinearOp<SCALAR >; \ 
  426  template RCP<LinearOpBase<SCALAR > > \ 
  428    const RCP<LinearOpBase<SCALAR > > &A, \ 
  429    const RCP<LinearOpBase<SCALAR > > &B, \ 
  430    const std::string &label \ 
  433  template RCP<const LinearOpBase<SCALAR > > \ 
  435    const RCP<const LinearOpBase<SCALAR > > &A, \ 
  436    const RCP<const LinearOpBase<SCALAR > > &B, \ 
  437    const std::string &label \ 
  440  template RCP<LinearOpBase<SCALAR > > \ 
  442    const RCP<LinearOpBase<SCALAR > > &A, \ 
  443    const RCP<LinearOpBase<SCALAR > > &B, \ 
  444    const std::string &label \ 
  447  template RCP<const LinearOpBase<SCALAR > > \ 
  449    const RCP<const LinearOpBase<SCALAR > > &A, \ 
  450    const RCP<const LinearOpBase<SCALAR > > &B, \ 
  451    const std::string &label \ 
virtual std::string description() const
 
Concrete composite LinearOpBase subclass that creates an implicitly added linear operator out of one ...
 
RCP< LinearOpBase< Scalar > > getNonconstOp(const int k)
 
void applyImpl(const EOpTransp M_trans, const MultiVectorBase< Scalar > &X, const Ptr< MultiVectorBase< Scalar > > &Y, const Scalar alpha, const Scalar beta) const
 
bool opIsConst(const int k) const
 
void uninitialize()
Set to uninitialized.
 
std::string description() const
Prints just the name DefaultAddedLinearOp along with the overall dimensions and the number of constit...
 
RCP< const VectorSpaceBase< Scalar > > domain() const
Returns this->getOp(this->numOps()-1).domain() if <t>this->numOps() > 0 and returns Teuchos::null oth...
 
RCP< const VectorSpaceBase< Scalar > > range() const
Returns this->getOp(0).range() if <t>this->numOps() > 0 and returns Teuchos::null otherwise.
 
void describe(Teuchos::FancyOStream &out, const Teuchos::EVerbosityLevel verbLevel) const
Prints the details about the constituent linear operators.
 
DefaultAddedLinearOp()
Constructs to uninitialized.
 
void initialize(const ArrayView< const RCP< LinearOpBase< Scalar > > > &Ops)
Initialize given a list of non-const linear operators.
 
bool opSupportedImpl(EOpTransp M_trans) const
Returns true only if all constituent operators support M_trans.
 
RCP< const LinearOpBase< Scalar > > clone() const
 
RCP< const LinearOpBase< Scalar > > getOp(const int k) const
 
Base class for all linear operators.
 
Interface for a collection of column vectors called a multi-vector.
 
#define TEUCHOS_TEST_FOR_EXCEPT(throw_exception_test)
 
#define THYRA_ASSERT_LINEAR_OP_MULTIVEC_APPLY_SPACES(FUNC_NAME, M, M_T, X, Y)
This is a very useful macro that should be used to validate that the spaces for the multi-vector vers...
 
#define THYRA_ASSERT_LINEAR_OP_PLUS_LINEAR_OP_SPACES_NAMES(FUNC_NAME, M1, M1_T, M1_N, M2, M2_T, M2_N)
Assert that a linear operator addition matches up.
 
EOpTransp
Enumeration for determining how a linear operator is applied. `*.
 
Teuchos::Ordinal Ordinal
Type for the dimension of a vector space. `*.
 
const char * toString(EConj conj)
Return a string name for a EOpTransp value. `*.
 
@ NOTRANS
Use the non-transposed operator.
 
T_To & dyn_cast(T_From &from)
 
std::string toString(const T &t)