ROL
ROL_StdTridiagonalOperator.hpp
Go to the documentation of this file.
1 // @HEADER
2 // *****************************************************************************
3 // Rapid Optimization Library (ROL) Package
4 //
5 // Copyright 2014 NTESS and the ROL contributors.
6 // SPDX-License-Identifier: BSD-3-Clause
7 // *****************************************************************************
8 // @HEADER
9 
10 #ifndef ROL_STDTRIDIAGONALOPERATOR_H
11 #define ROL_STDTRIDIAGONALOPERATOR_H
12 
14 
31 namespace ROL {
32 
33 template <class Real>
35 
36  template <typename T> using vector = std::vector<T>;
37 
38 private:
39 
40  const ROL::Ptr<const vector<Real> > a_; // Diagonal
41  const ROL::Ptr<const vector<Real> > b_; // Superdiagonal
42  const ROL::Ptr<const vector<Real> > c_; // Subdiagonal
43 
44  mutable vector<Real> dl_;
45  mutable vector<Real> d_;
46  mutable vector<Real> du_;
47  mutable vector<Real> du2_;
48 
49  mutable vector<int> ipiv_;
50 
51  int N_;
52 
53  ROL::LAPACK<int,Real> lapack_;
54 
55  void copy(void) const {
56  for(int i=0;i<N_-1;++i) {
57  dl_[i] = (*c_)[i];
58  d_[i] = (*a_)[i];
59  du_[i] = (*b_)[i];
60  }
61  d_[N_-1] = (*a_)[N_-1];
62  du2_.assign(N_-2,0.0);
63  }
64 
65 public:
66 
67  StdTridiagonalOperator( const ROL::Ptr<const vector<Real> > &a,
68  const ROL::Ptr<const vector<Real> > &b,
69  const ROL::Ptr<const vector<Real> > &c ) :
70  StdLinearOperator<Real>(), a_(a), b_(b), c_(c) {
71 
72  N_ = a_->size();
73 
74  dl_.resize(N_-1);
75  d_.resize(N_);
76  du_.resize(N_-1);
77  du2_.resize(N_-2);
78  ipiv_.resize(N_);
79  }
80 
81  StdTridiagonalOperator( const ROL::Ptr<const vector<Real> > &a,
82  const ROL::Ptr<const vector<Real> > &b ) {
83  StrdTridiagonalOperator(a,b,b);
84  }
85 
86 
88 
93 
94 
95  virtual void apply( vector<Real> &Hv, const vector<Real> &v, Real &tol ) const {
96  Hv[0] = (*a_)[0]*v[0] + (*b_)[0]*v[1];
97 
98  for( int i=1; i<N_-1; ++i ) {
99  Hv[i] = (*c_)[i-1]*v[i-1] + (*a_)[i]*v[i] + (*b_)[i]*v[i+1];
100  }
101 
102  Hv[N_-1] = (*a_)[N_-1]*v[N_-1] + (*c_)[N_-2]*v[N_-2];
103 
104  }
105 
106  virtual void applyAdjoint( vector<Real> &Hv, const vector<Real> &v, Real &tol ) const {
107  Hv[0] = (*a_)[0]*v[0] + (*c_)[0]*v[1];
108 
109  for( int i=1; i<N_-1; ++i ) {
110  Hv[i] = (*b_)[i-1]*v[i-1] + (*a_)[i]*v[i] + (*c_)[i]*v[i+1];
111  }
112 
113  Hv[N_-1] = (*a_)[N_-1]*v[N_-1] + (*b_)[N_-2]*v[N_-2];
114  }
115 
116  virtual void applyInverse( vector<Real> &Hv, const vector<Real> &v, Real &tol ) const {
117  Hv = v;
118  copy();
119  int INFO;
120  lapack_.GTTRF(N_,&dl_[0],&d_[0],&du_[0],&du2_[0],&ipiv_[0],&INFO);
121  lapack_.GTTRS('N',N_,1,&dl_[0],&d_[0],&du_[0],&du2_[0],&ipiv_[0],&Hv[0],N_,&INFO);
122 }
123 
124  virtual void applyAdjointInverse( vector<Real> &Hv, const vector<Real> &v, Real &tol ) const {
125  Hv = v;
126  copy();
127  int INFO;
128  lapack_.GTTRF(N_,&dl_[0],&d_[0],&du_[0],&du2_[0],&ipiv_[0],&INFO);
129  lapack_.GTTRS('T',N_,1,&dl_[0],&d_[0],&du_[0],&du2_[0],&ipiv_[0],&Hv[0],N_,&INFO);
130  }
131 
132 }; // class StdTridiagonalOperator
133 
134 } // namespace ROL
135 
136 #endif
Provides the std::vector implementation to apply a linear operator, which is a std::vector representa...
StdTridiagonalOperator(const ROL::Ptr< const vector< Real > > &a, const ROL::Ptr< const vector< Real > > &b, const ROL::Ptr< const vector< Real > > &c)
virtual void applyAdjoint(vector< Real > &Hv, const vector< Real > &v, Real &tol) const
StdTridiagonalOperator(const ROL::Ptr< const vector< Real > > &a, const ROL::Ptr< const vector< Real > > &b)
virtual void applyInverse(vector< Real > &Hv, const vector< Real > &v, Real &tol) const
Provides the std::vector implementation to apply a linear operator, which encapsulates a tridiagonal ...
const ROL::Ptr< const vector< Real > > c_
virtual void apply(vector< Real > &Hv, const vector< Real > &v, Real &tol) const
virtual void applyAdjointInverse(vector< Real > &Hv, const vector< Real > &v, Real &tol) const
const ROL::Ptr< const vector< Real > > b_
const ROL::Ptr< const vector< Real > > a_