MOOCHO (Single Doxygen Collection)  Version of the Day
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
MoochoPack_CheckDecompositionFromRPy_Step.cpp
Go to the documentation of this file.
1 // @HEADER
2 // ***********************************************************************
3 //
4 // Moocho: Multi-functional Object-Oriented arCHitecture for Optimization
5 // Copyright (2003) Sandia Corporation
6 //
7 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
8 // license for use of this work by or on behalf of the U.S. Government.
9 //
10 // Redistribution and use in source and binary forms, with or without
11 // modification, are permitted provided that the following conditions are
12 // met:
13 //
14 // 1. Redistributions of source code must retain the above copyright
15 // notice, this list of conditions and the following disclaimer.
16 //
17 // 2. Redistributions in binary form must reproduce the above copyright
18 // notice, this list of conditions and the following disclaimer in the
19 // documentation and/or other materials provided with the distribution.
20 //
21 // 3. Neither the name of the Corporation nor the names of the
22 // contributors may be used to endorse or promote products derived from
23 // this software without specific prior written permission.
24 //
25 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
26 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
28 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
29 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
30 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
31 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
32 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
33 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
34 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
35 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36 //
37 // Questions? Contact Roscoe A. Bartlett (rabartl@sandia.gov)
38 //
39 // ***********************************************************************
40 // @HEADER
41 
42 #include <typeinfo>
43 
50 
51 namespace MoochoPack {
52 
54  const new_decomp_strategy_ptr_t &new_decomp_strategy
55  ,value_type max_decomposition_cond_change_frac
56  )
57  :new_decomp_strategy_(new_decomp_strategy)
58  ,max_decomposition_cond_change_frac_(max_decomposition_cond_change_frac)
59 {
60  reset();
61 }
62 
65 }
66 
67 // Overridden
68 
70  , IterationPack::EDoStepType type, poss_type assoc_step_poss )
71 {
72  NLPAlgo &algo = rsqp_algo(_algo);
73  NLPAlgoState &s = algo.rsqp_state();
74  const Range1D equ_decomp = s.equ_decomp();
75  EJournalOutputLevel olevel = algo.algo_cntr().journal_output_level();
76  std::ostream &out = algo.track().journal_out();
77 
78  // print step header.
79  if( static_cast<int>(olevel) >= static_cast<int>(PRINT_ALGORITHM_STEPS) ) {
81  print_algorithm_step( algo, step_poss, type, assoc_step_poss, out );
82  }
83 
84  bool select_new_decomposition = false;
85 
86  // Compute: resid = (Gc(decomp)'*Y) * py + c(decomp)
87  const Vector &py_k = s.py().get_k(0);
88  const Vector &c_k = s.c().get_k(0);
89  Vector::vec_ptr_t c_decomp_k = c_k.sub_view(equ_decomp);
90  VectorMutable::vec_mut_ptr_t resid = c_decomp_k->space().create_member();
91 
92  // resid = R*py + c(equ_decomp)
93  LinAlgOpPack::V_MtV( resid.get(), s.R().get_k(0), BLAS_Cpp::no_trans, py_k );
94  LinAlgOpPack::Vp_V( resid.get(), *c_decomp_k );
95 
96  const value_type
98  epsilon = std::numeric_limits<value_type>::epsilon(),
99  nrm_resid = resid->norm_inf(),
100  nrm_c_decomp = c_decomp_k->norm_inf(),
101  beta = nrm_resid / (nrm_c_decomp+small_num);
102 
103  if( (int)olevel >= (int)PRINT_ALGORITHM_STEPS ) {
104  out << "\nbeta = ||R*py_k + c_k(decomp)||inf / (||c_k(decomp)||inf + small_number)"
105  << "\n = "<<nrm_resid<<" / ("<<nrm_c_decomp<<" + "<<small_num<<")"
106  << "\n = " << beta << std::endl;
107  }
108 
109  // Check to see if a new basis was selected or not
110  IterQuantityAccess<index_type>
111  &num_basis_iq = s.num_basis();
112  if( num_basis_iq.updated_k(0) ) {
113  if( (int)olevel >= (int)PRINT_ALGORITHM_STEPS )
114  out << "\nnum_basis_k was updated so the basis changed so we will skip this check\n"
115  << " reset min ||R*py+c||/||c|| to current value + epsilon(" << epsilon << ")\n";
116  beta_min_ = beta + epsilon;
117  return true;
118  }
119 
120  if( beta != 0.0 ) {
121  if( beta < beta_min_ ) {
122  beta_min_ = beta;
123  }
124  else {
125  if( beta / beta_min_ > max_decomposition_cond_change_frac() ) {
126  if( (int)olevel >= (int)PRINT_BASIC_ALGORITHM_INFO ) {
127  out
128  << "\nbeta_change = ( ||R*py+c||/||c|| = " << beta
129  << " ) / ( min ||R*py+c||/||c|| = " << beta_min_ << " )\n"
130  << " = " << (beta/beta_min_) << " > max_decomposition_cond_change_frac = "
131  << max_decomposition_cond_change_frac()
132  << "\n\nSelecting a new decomposition"
133  << " (k = " << algo.state().k() << ") ...\n";
134  }
135  select_new_decomposition = true;
136  }
137  }
138  if(select_new_decomposition) {
139  reset();
140  return new_decomp_strategy().new_decomposition(algo,step_poss,type,assoc_step_poss);
141  }
142  }
143  return true;
144 }
145 
147  , IterationPack::EDoStepType type, poss_type assoc_step_poss
148  , std::ostream& out, const std::string& L ) const
149 {
150  out
151  << L << "*** Try to detect when the decomposition is becomming illconditioned\n"
152  << L << "default: beta_min = inf\n"
153  << L << " max_decomposition_cond_change_frac = " << max_decomposition_cond_change_frac() << std::endl
154  << L << "beta = norm_inf(R*py_k + c_k(decomp)) / (norm_inf(c_k(decomp))+small_number)\n"
155  << L << "select_new_decomposition = false\n"
156  << L << "if num_basis_k is updated then\n"
157  << L << " beta_min = beta\n"
158  << L << "end\n"
159  << L << "if beta < beta_min then\n"
160  << L << " beta_min = beta\n"
161  << L << "else\n"
162  << L << " if beta/ beta_min > max_decomposition_cond_change_frac then\n"
163  << L << " select_new_decomposition = true\n"
164  << L << " end\n"
165  << L << "end\n"
166  << L << "if select_new_decomposition == true then\n"
167  << L << " new decomposition selection : " << typeName(new_decomp_strategy()) << std::endl
168  ;
169  new_decomp_strategy().print_new_decomposition(
170  rsqp_algo(algo),step_poss,type,assoc_step_poss,out, L + " " );
171  out
172  << L << " end new decomposition selection\n"
173  << L << "end\n"
174  ;
175 }
176 
177 } // end namespace MoochoPack
std::string typeName(const T &t)
rSQP Algorithm control class.
Not transposed.
virtual std::ostream & journal_out() const
Return a reference to a std::ostream to be used to output debug information and the like...
void reset()
Call the reset initialization of all defaults.
EJournalOutputLevel
enum for journal output.
Reduced space SQP state encapsulation interface.
std::ostream * out
void print_algorithm_step(const Algorithm &algo, Algorithm::poss_type step_poss, EDoStepType type, Algorithm::poss_type assoc_step_poss, std::ostream &out)
Prints to 'out' the algorithm step.
AlgorithmTracker & track()
AlgorithmState & state()
bool do_step(Algorithm &algo, poss_type step_poss, IterationPack::EDoStepType type, poss_type assoc_step_poss)
void V_MtV(VectorMutable *v_lhs, const MatrixOp &M_rhs1, BLAS_Cpp::Transp trans_rhs1, const V &V_rhs2)
v_lhs = op(M_rhs1) * V_rhs2.
AbstractLinAlgPack::value_type value_type
Acts as the central hub for an iterative algorithm.
NLPAlgoState & rsqp_state()
<<std aggr>="">> members for algo_cntr
NLPAlgo & rsqp_algo(Algorithm &algo)
Convert from a Algorithm to a NLPAlgo.
void print_step(const Algorithm &algo, poss_type step_poss, IterationPack::EDoStepType type, poss_type assoc_step_poss, std::ostream &out, const std::string &leading_str) const
void Vp_V(VectorMutable *v_lhs, const V &V_rhs)
v_lhs += V_rhs.