26 bundle_(
ROL::nullPtr), lineSearch_(
ROL::nullPtr),
27 QPiter_(0), QPmaxit_(0), QPtol_(0), step_flag_(0),
28 T_(0), tol_(0), m1_(0), m2_(0), m3_(0), nu_(0),
29 ls_maxit_(0), first_print_(true), isConvex_(false) {
35 const Real
zero(0), two(2), oem3(1.e-3), oem6(1.e-6), oem8(1.e-8);
36 const Real p1(0.1), p2(0.2), p9(0.9), oe3(1.e3), oe8(1.e8);
37 ParameterList &blist = parlist.sublist(
"Step").sublist(
"Bundle");
38 state_->searchSize = blist.get(
"Initial Trust-Region Parameter", oe3);
39 T_ = blist.get(
"Maximum Trust-Region Parameter", oe8);
40 tol_ = blist.get(
"Epsilon Solution Tolerance", oem6);
41 m1_ = blist.get(
"Upper Threshold for Serious Step", p1);
42 m2_ = blist.get(
"Lower Threshold for Serious Step", p2);
43 m3_ = blist.get(
"Upper Threshold for Null Step", p9);
44 nu_ = blist.get(
"Tolerance for Trust-Region Parameter", oem3);
47 Real coeff = blist.get(
"Distance Measure Coefficient",
zero);
48 Real omega = blist.get(
"Locality Measure Coefficient", two);
49 unsigned maxSize = blist.get(
"Maximum Bundle Size", 200);
50 unsigned remSize = blist.get(
"Removal Size for Bundle Update", 2);
51 int cps = blist.get(
"Cutting Plane Solver",0);
53 bundle_ = makePtr<Bundle_U_TT<Real>>(maxSize,coeff,omega,remSize);
56 bundle_ = makePtr<Bundle_U_AS<Real>>(maxSize,coeff,omega,remSize);
61 QPtol_ = blist.get(
"Cutting Plane Tolerance", oem8);
62 QPmaxit_ = blist.get(
"Cutting Plane Iteration Limit", 1000);
65 ParameterList &lslist = parlist.sublist(
"Step").sublist(
"Line Search");
66 ls_maxit_ = lslist.get(
"Maximum Number of Function Evaluations",20);
72 verbosity_ = parlist.sublist(
"General").get(
"Output Level", 0);
101 std::ostream &outStream ) {
102 const Real
zero(0), two(2), half(0.5);
104 Real tol(std::sqrt(ROL_EPSILON<Real>()));
105 initialize(x,g,obj,outStream);
106 Ptr<Vector<Real>> y = x.
clone();
107 Ptr<Vector<Real>> aggSubGradNew = g.
clone();
108 Real aggSubGradOldNorm = state_->gnorm;
109 Real linErrNew(0), valueNew(0);
110 Real aggLinErrNew(0), aggLinErrOld(0), aggDistMeasNew(0);
111 Real v(0), l(0), u(T_), gd(0);
115 if (verbosity_ > 0) writeOutput(outStream,
true);
117 while (status_->check(*state_)) {
118 first_print_ =
false;
119 QPiter_ = (step_flag_==1 ? 0 : QPiter_);
126 QPiter_ += bundle_->solveDual(state_->searchSize,QPmaxit_,QPtol_);
127 bundle_->aggregate(*aggSubGradNew,aggLinErrNew,aggDistMeasNew);
128 state_->aggregateGradientNorm = aggSubGradNew->norm();
129 if (verbosity_ > 1) {
130 outStream << std::endl;
131 outStream <<
" Computation of aggregrate quantities" << std::endl;
132 outStream <<
" Aggregate subgradient norm: " << state_->aggregateGradientNorm << std::endl;
133 outStream <<
" Aggregate linearization error: " << aggLinErrNew << std::endl;
134 outStream <<
" Aggregate distance measure: " << aggDistMeasNew << std::endl;
139 v = -state_->searchSize*std::pow(state_->aggregateGradientNorm,two)-aggLinErrNew;
140 state_->stepVec->set(aggSubGradNew->dual());
141 state_->stepVec->scale(-state_->searchSize);
142 state_->snorm = state_->searchSize*state_->aggregateGradientNorm;
143 if (verbosity_ > 1) {
144 outStream << std::endl;
145 outStream <<
" Solve cutting plan subproblem" << std::endl;
146 outStream <<
" Cutting plan objective value: " << v << std::endl;
147 outStream <<
" Norm of computed step: " << state_->snorm << std::endl;
148 outStream <<
" 'Trust-region' radius: " << state_->searchSize << std::endl;
153 if (std::max(state_->aggregateGradientNorm,aggLinErrNew) <= tol_) {
155 state_->stepVec->zero(); state_->snorm =
zero;
161 else if (std::isnan(state_->aggregateGradientNorm)
162 || std::isnan(aggLinErrNew)
163 || (std::isnan(aggDistMeasNew) && !isConvex_)) {
164 state_->stepVec->zero(); state_->snorm =
zero;
171 y->set(x); y->plus(*state_->stepVec);
173 valueNew = obj.
value(*y,tol);
175 obj.
gradient(*state_->gradientVec,*y,tol);
179 gd = state_->stepVec->apply(*state_->gradientVec);
180 linErrNew = state_->value - (valueNew - gd);
182 Real eps =
static_cast<Real
>(10)*ROL_EPSILON<Real>();
183 Real del = eps*std::max(
static_cast<Real
>(1),std::abs(state_->value));
184 Real Df = (valueNew - state_->value) - del;
187 if (std::abs(Df) < eps && std::abs(Dm) < eps) {
195 bool NS2a = (bundle_->computeAlpha(state_->snorm,linErrNew) <= m3_*aggLinErrOld);
196 bool NS2b = (std::abs(state_->value-valueNew) <= aggSubGradOldNorm + aggLinErrOld);
197 if (verbosity_ > 1) {
198 outStream << std::endl;
199 outStream <<
" Check for serious/null step" << std::endl;
200 outStream <<
" Serious step test SS(i): " << SS1 << std::endl;
201 outStream <<
" -> Left hand side: " << valueNew-state_->value << std::endl;
202 outStream <<
" -> Right hand side: " << m1_*v << std::endl;
203 outStream <<
" Null step test NS(iia): " << NS2a << std::endl;
204 outStream <<
" -> Left hand side: " << bundle_->computeAlpha(state_->snorm,linErrNew) << std::endl;
205 outStream <<
" -> Right hand side: " << m3_*aggLinErrOld << std::endl;
206 outStream <<
" Null step test NS(iib): " << NS2b << std::endl;
207 outStream <<
" -> Left hand side: " << std::abs(state_->value-valueNew) << std::endl;
208 outStream <<
" -> Right hand side: " << aggSubGradOldNorm + aggLinErrOld << std::endl;
213 bool SS2 = (gd >= m2_*v || state_->searchSize >= T_-nu_);
214 if (verbosity_ > 1) {
215 outStream <<
" Serious step test SS(iia): " << (gd >= m2_*v) << std::endl;
216 outStream <<
" -> Left hand side: " << gd << std::endl;
217 outStream <<
" -> Right hand side: " << m2_*v << std::endl;
218 outStream <<
" Serious step test SS(iia): " << (state_->searchSize >= T_-nu_) << std::endl;
219 outStream <<
" -> Left hand side: " << state_->searchSize << std::endl;
220 outStream <<
" -> Right hand side: " << T_-nu_ << std::endl;
225 if (verbosity_ > 1) {
226 outStream <<
" Serious step taken" << std::endl;
231 l = state_->searchSize;
232 state_->searchSize = half*(u+l);
233 if (verbosity_ > 1) {
234 outStream <<
" Increase 'trust-region' radius: " << state_->searchSize << std::endl;
239 if ( NS2a || NS2b ) {
240 state_->stepVec->zero(); state_->snorm =
zero;
243 if (verbosity_ > 1) {
244 outStream <<
" Null step taken" << std::endl;
249 u = state_->searchSize;
250 state_->searchSize = half*(u+l);
251 if (verbosity_ > 1) {
252 outStream <<
" Decrease 'trust-region' radius: " << state_->searchSize << std::endl;
259 bool NS3 = (gd - bundle_->computeAlpha(state_->snorm,linErrNew) >= m2_*v);
260 if (verbosity_ > 1) {
261 outStream <<
" Null step test NS(iii): " << NS3 << std::endl;
262 outStream <<
" -> Left hand side: " << gd - bundle_->computeAlpha(state_->snorm,linErrNew) << std::endl;
263 outStream <<
" -> Right hand side: " << m2_*v << std::endl;
271 if ( NS2a || NS2b ) {
273 state_->stepVec->zero();
281 int ls_nfval = 0, ls_ngrad = 0;
282 lineSearch_->run(alpha,valueNew,ls_nfval,ls_ngrad,gd,*state_->stepVec,x,obj);
283 if ( ls_nfval == ls_maxit_ ) {
284 state_->stepVec->zero();
290 state_->stepVec->scale(alpha);
297 u = state_->searchSize;
298 state_->searchSize = half*(u+l);
303 u = state_->searchSize;
304 state_->searchSize = half*(u+l);
313 state_->aggregateModelError = aggLinErrNew;
314 aggSubGradOldNorm = state_->aggregateGradientNorm;
315 aggLinErrOld = aggLinErrNew;
317 if ( !state_->flag ) {
321 bundle_->reset(*aggSubGradNew,aggLinErrNew,state_->snorm);
325 if ( step_flag_==1 ) {
327 x.
plus(*state_->stepVec);
328 Real valueOld = state_->value;
329 state_->value = valueNew;
330 bundle_->update(step_flag_,valueNew-valueOld,state_->snorm,*state_->gradientVec,*state_->stepVec);
332 else if ( step_flag_==0 ) {
334 bundle_->update(step_flag_,linErrNew,state_->snorm,*state_->gradientVec,*state_->stepVec);
340 state_->iterateVec->set(x);
341 state_->gnorm = state_->gradientVec->norm();
342 if ( step_flag_==1 ) {
347 if (verbosity_ > 0) writeOutput(outStream,printHeader_);
379 std::ios_base::fmtflags osFlags(os.flags());
380 os << std::scientific << std::setprecision(6);
381 if ( state_->iter == 0 && first_print_ ) {
383 if ( print_header ) {
387 os << std::setw(6) << std::left << state_->iter;
388 os << std::setw(15) << std::left << state_->value;
389 os << std::setw(15) << std::left << state_->gnorm;
390 os << std::setw(15) << std::left <<
"---";
391 os << std::setw(10) << std::left << state_->nfval;
392 os << std::setw(10) << std::left << state_->ngrad;
393 os << std::setw(15) << std::left <<
"---";
394 os << std::setw(15) << std::left <<
"---";
395 os << std::setw(15) << std::left << state_->searchSize;
396 os << std::setw(10) << std::left <<
"---";
399 if ( step_flag_==1 && state_->iter > 0 ) {
400 if ( print_header ) {
405 os << std::setw(6) << std::left << state_->iter;
406 os << std::setw(15) << std::left << state_->value;
407 os << std::setw(15) << std::left << state_->gnorm;
408 os << std::setw(15) << std::left << state_->snorm;
409 os << std::setw(10) << std::left << state_->nfval;
410 os << std::setw(10) << std::left << state_->ngrad;
411 os << std::setw(15) << std::left << state_->aggregateGradientNorm;
412 os << std::setw(15) << std::left << state_->aggregateModelError;
413 os << std::setw(15) << std::left << state_->searchSize;
414 os << std::setw(10) << std::left << QPiter_;