00001
00002
00003
00004
00005
00006
00011 #include <sstream>
00012 using std::istringstream;
00013
00014 # include <admodel.h>
00015 # include <df1b2fun.h>
00016 # include <adrndeff.h>
00017 static int no_stuff=0;
00018
00023 void function_minimizer::quasi_newton_block(int nvar,int _crit,
00024 independent_variables& x,const dvector& _g,const double& _f)
00025 {
00026 int ifn_trap=0;
00027 int itn_trap=0;
00028 int on=0;
00029 int nopt=0;
00030 if ( (on=option_match(ad_comm::argc,ad_comm::argv,"-fntrap",nopt))>-1)
00031 {
00032 if (nopt !=2)
00033 {
00034 cerr <<
00035 "Usage -fntrap option needs two non-negative integers -- ignored.\n";
00036 }
00037 else
00038 {
00039 ifn_trap=atoi(ad_comm::argv[on+1]);
00040 itn_trap=atoi(ad_comm::argv[on+2]);
00041 }
00042 }
00043
00044 double & f= (double&)_f;
00045 dvector & g= (dvector&)_g;
00046
00047
00048
00049 fmm fmc(negdirections ? negdirections->indexmax() : nvar);
00050 int on1;
00051 if ( (on1=option_match(ad_comm::argc,ad_comm::argv,"-nox"))>-1)
00052 {
00053 fmc.noprintx=1;
00054 }
00055 fmc.maxfn= maxfn;
00056 if ( (on1=option_match(ad_comm::argc,ad_comm::argv,"-dd",nopt))>-1)
00057 {
00058 if (!nopt)
00059 {
00060 cerr << "Usage -iprint option needs integer -- ignored" << endl;
00061
00062 }
00063 else
00064 {
00065 int jj=atoi(ad_comm::argv[on1+1]);
00066 fmc.dcheck_flag=jj;
00067 }
00068 }
00069 nopt=0;
00070 if ( (on1=option_match(ad_comm::argc,ad_comm::argv,"-iprint",nopt))>-1)
00071 {
00072 if (!nopt)
00073 {
00074 cerr << "Usage -iprint option needs integer -- ignored" << endl;
00075 fmc.iprint=iprint;
00076 }
00077 else
00078 {
00079 int jj=atoi(ad_comm::argv[on1+1]);
00080 fmc.iprint=jj;
00081 }
00082 }
00083 else
00084 {
00085 fmc.iprint= iprint;
00086 }
00087 fmc.crit = crit;
00088 fmc.imax = imax;
00089 fmc.dfn= dfn;
00090
00091 double _dfn=1.e-2;
00092 if ( (on=option_match(ad_comm::argc,ad_comm::argv,"-dfn",nopt))>-1)
00093 {
00094 if (!nopt)
00095 {
00096 cerr << "Usage -dfn option needs number -- ignored" << endl;
00097 }
00098 else
00099 {
00100 istringstream ist(ad_comm::argv[on+1]);
00101 ist >> _dfn;
00102
00103 if (_dfn<=0)
00104 {
00105 cerr << "Usage -dfn option needs positive number -- ignored" << endl;
00106 _dfn=0.0;
00107 }
00108 }
00109 }
00110 if (_dfn>0)
00111 {
00112 fmc.dfn=_dfn;
00113 }
00114
00115 fmc.scroll_flag= scroll_flag;
00116 fmc.min_improve=min_improve;
00117 gradient_structure::set_YES_DERIVATIVES();
00118
00119 if (_crit)
00120 {
00121 fmc.crit = _crit;
00122 }
00123 if (!(!convergence_criteria))
00124 {
00125 int ind=min(convergence_criteria.indexmax(),
00126 initial_params::current_phase);
00127 fmc.crit=convergence_criteria(ind);
00128 }
00129 if (!(!maximum_function_evaluations))
00130 {
00131 int ind=min(maximum_function_evaluations.indexmax(),
00132 initial_params::current_phase);
00133 fmc.maxfn= (int) maximum_function_evaluations(ind);
00134 }
00135 int unvar=1;
00136 if (random_effects_flag)
00137 {
00138 initial_params::set_active_only_random_effects();
00139
00140 unvar=initial_params::nvarcalc();
00141 initial_params::restore_start_phase();
00142 initial_params::set_inactive_random_effects();
00143 int nvar1=initial_params::nvarcalc();
00144 if (nvar1 != nvar)
00145 {
00146 cerr << "failed sanity check in "
00147 "void function_minimizer::quasi_newton_block" << endl;
00148 ad_exit(1);
00149 }
00150 }
00151
00152 if (!random_effects_flag || !unvar)
00153 {
00154 dvariable xf=initial_params::reset(dvar_vector(x));
00155 reset_gradient_stack();
00156 gradcalc(0,g);
00157 if (negdirections==0)
00158 {
00159 while (fmc.ireturn>=0)
00160 {
00161 fmc.fmin(f,x,g);
00162 if (fmc.ireturn>0)
00163 {
00164 dvariable vf=0.0;
00165 vf=initial_params::reset(dvar_vector(x));
00166 *objective_function_value::pobjfun=0.0;
00167 pre_userfunction();
00168 if ( no_stuff ==0 && quadratic_prior::get_num_quadratic_prior()>0)
00169 {
00170 quadratic_prior::get_M_calculations();
00171 }
00172 vf+=*objective_function_value::pobjfun;
00173 f=value(vf);
00174 gradcalc(nvar,g);
00175 }
00176 }
00177 }
00178 else
00179 {
00180 int i;
00181 int nx=negdirections->indexmax();
00182 independent_variables u(1,nx);
00183 dvector gu(1,nx);
00184 for (i=1;i<=nx;i++) u(i)=1.e-3;
00185 dvector x0(1,x.indexmax());
00186 x0=x;
00187 while (fmc.ireturn>=0)
00188 {
00189 fmc.fmin(f,u,gu);
00190 if (fmc.ireturn>0)
00191 {
00192 dvariable vf=0.0;
00193 x=x0;
00194 for (i=1;i<=nx;i++)
00195 {
00196 x+=u(i)*(*negdirections)(i);
00197 }
00198 vf=initial_params::reset(dvar_vector(x));
00199 *objective_function_value::pobjfun=0.0;
00200 pre_userfunction();
00201 if ( no_stuff ==0 && quadratic_prior::get_num_quadratic_prior()>0)
00202 {
00203 quadratic_prior::get_M_calculations();
00204 }
00205 vf+=*objective_function_value::pobjfun;
00206 f=value(vf);
00207 gradcalc(nvar,g);
00208 gu=(*negdirections)*g;
00209 }
00210 }
00211 x=x0;
00212 for (i=1;i<=nx;i++)
00213 {
00214 x+=u(i)*(*negdirections)(i);
00215 }
00216 delete negdirections;
00217 negdirections=0;
00218 }
00219 }
00220 else
00221 {
00222
00223
00224
00225
00226 initial_params::set_active_only_random_effects();
00227
00228 int _unvar=initial_params::nvarcalc();
00229
00230
00231 if (funnel_init_var::py)
00232 {
00233 delete funnel_init_var::py;
00234 funnel_init_var::py=0;
00235 }
00236 if (lapprox)
00237 {
00238 delete lapprox;
00239 lapprox = NULL;
00240
00241 deallocate();
00242 df1b2variable::pool->deallocate();
00243
00244 for (int i=1;i<df1b2variable::adpool_counter;i++)
00245 {
00246 delete df1b2variable::adpool_vector[i];
00247 df1b2variable::adpool_vector[i]=0;
00248 df1b2variable::nvar_vector[i]=0;
00249 }
00250 df1b2variable::adpool_counter=0;
00251 }
00252 lapprox=new laplace_approximation_calculator(nvar,_unvar,1,nvar+_unvar,
00253 this);
00254 if (lapprox == NULL)
00255 {
00256 cerr << "Error allocating memory for lapprox" << endl;
00257 ad_exit(1);
00258 }
00259 initial_df1b2params::current_phase=initial_params::current_phase;
00260
00261 initial_df1b2params::save_varsptr();
00262 allocate();
00263 initial_df1b2params::restore_varsptr();
00264
00265 df1b2_gradlist::set_no_derivatives();
00266 dvector y(1,initial_params::nvarcalc_all());
00267 initial_params::xinit_all(y);
00268 initial_df1b2params::reset_all(y);
00269
00270 gradient_structure::set_NO_DERIVATIVES();
00271
00272
00273 if (lapprox->have_users_hesstype==0)
00274 {
00275 if (initial_df1b2params::separable_flag)
00276 {
00277 if ( (on=option_match(ad_comm::argc,ad_comm::argv,"-newht",nopt))>-1)
00278 {
00279 lapprox->check_hessian_type2(this);
00280 }
00281 else
00282 {
00283 lapprox->check_hessian_type(this);
00284 }
00285
00286
00287 switch(lapprox->hesstype)
00288 {
00289 case 1:
00290 cout << "Hessian type 1 " << endl;
00291 break;
00292 case 2:
00293 cout << "\nBlock diagonal Hessian (Block size =" <<
00294 (lapprox->usize)/(lapprox->num_separable_calls) << ")\n" << endl;
00295 break;
00296 case 3:
00297 cout << "\nBanded Hessian (Band width = " << lapprox->bw << ")\n"
00298 << endl;
00299 break;
00300 case 4:
00301 cout << "Hessian type 4 " << endl;
00302 break;
00303 default:
00304 cerr << "This can't happen" << endl;
00305 ad_exit(1);
00306 }
00307 }
00308 }
00309
00310
00311
00312
00313
00314
00315
00316
00317 if (laplace_approximation_calculator::variance_components_vector)
00318 {
00319 #ifdef DIAG
00320 if (!lapprox)
00321 {
00322 cerr << "this can't happen" << endl;
00323 ad_exit(1);
00324 }
00325 #endif
00326 lapprox->get_hessian_components_banded_lme(this);
00327 }
00328
00329 if (negdirections==0)
00330 {
00331 while (fmc.ireturn>=0)
00332 {
00333 fmc.fmin(f,x,g);
00334 if (fmc.ireturn>0)
00335 {
00336 if (ifn_trap)
00337 {
00338 if (ifn_trap==fmc.ifn && itn_trap == fmc.itn)
00339 {
00340 cout << "we are here" << endl;
00341 }
00342 }
00343 g=(*lapprox)(x,f,this);
00344 if (bad_step_flag==1)
00345 {
00346 g=1.e+4;
00347 f=2.*fmc.fbest;
00348 bad_step_flag=0;
00349 }
00350
00351 if (lapprox->init_switch==0)
00352 {
00353 if (f<fmc.fbest)
00354 {
00355 lapprox->ubest=lapprox->uhat;
00356 }
00357 }
00358 }
00359 }
00360 }
00361 else
00362 {
00363 int i;
00364 int nx=negdirections->indexmax();
00365 independent_variables u(1,nx);
00366 dvector x0(1,x.indexmax());
00367 x0=x;
00368 dvector gu(1,nx);
00369 for (i=1;i<=nx;i++) u(i)=1.e-3;
00370 while (fmc.ireturn>=0)
00371 {
00372 fmc.fmin(f,u,gu);
00373 if (fmc.ireturn>0)
00374 {
00375 x=x0;
00376 for (i=1;i<=nx;i++)
00377 {
00378 x+=u(i)*(*negdirections)(i);
00379 }
00380 g=(*lapprox)(x,f,this);
00381 gu=(*negdirections)*g;
00382 }
00383 }
00384 x=x0;
00385 for (i=1;i<=nx;i++)
00386 {
00387 x+=u(i)*(*negdirections)(i);
00388 }
00389 delete negdirections;
00390 negdirections=0;
00391 }
00392 initial_params::set_inactive_only_random_effects();
00393 }
00394
00395 if (funnel_init_var::py)
00396 {
00397 delete funnel_init_var::py;
00398 funnel_init_var::py=0;
00399 }
00400 gradient_structure::set_NO_DERIVATIVES();
00401 ffbest=fmc.fbest;
00402 g=fmc.gbest(1,fmc.gbest.indexmax());
00403 iexit=fmc.iexit;
00404 ifn=fmc.ifn;
00405 ihflag=fmc.ihflag;
00406 ihang=fmc.ihang;
00407 maxfn_flag=fmc.maxfn_flag;
00408 quit_flag=fmc.quit_flag;
00409 objective_function_value::gmax=fabs(fmc.gmax);
00410 }