/home/coin/SVN-release/OS-2.4.1/Bonmin/src/Interfaces/BonTNLPSolver.cpp

Go to the documentation of this file.
00001 // (C) Copyright International Business Machines Corporation, 2006
00002 // All Rights Reserved.
00003 // This code is published under the Common Public License.
00004 //
00005 // Authors :
00006 // Pierre Bonami, International Business Machines Corporation
00007 //
00008 // Date : 10/02/2006
00009 
00010 //Bonmin includes
00011 #include "BonTNLPSolver.hpp"
00012 
00013 //Ipopt includes
00014 #include "IpBlas.hpp"
00015 
00016 //Standard includes
00017 #include <fstream>
00018 
00019 #include "BonColReader.hpp"
00020 
00021 
00022 namespace Bonmin{
00023   using namespace Ipopt;
00024 
00025   
00026 #if 0
00027   string TNLPSolver::returnCodes[TNLPSolver::numReturnCodes] = {
00028     "Hit iteration limit" ,
00029     "Some error was made in computations." ,
00030     "Problem has more equations than free variables." ,
00031     "Problem is not well defined.",
00032     "Illegal option set.",
00033     "Exception in some the third-party code used by solver." ,
00034     "Unrecognized exception.",
00035     "Problem solved to optimality",
00036     "Problem solvedd to acceptable level of tolerance",
00037     "Problem is infeasible" ,
00038     "Problem is unbounded", };
00039 #endif
00040     
00041     
00042   TNLPSolver::TNLPSolver():
00043     start_time_(0),
00044     time_limit_(DBL_MAX)
00045   {
00046     initializeOptionsAndJournalist();
00047   }
00048 
00049   TNLPSolver::TNLPSolver(Ipopt::SmartPtr<Bonmin::RegisteredOptions> roptions,
00050     Ipopt::SmartPtr<Ipopt::OptionsList> options,
00051     Ipopt::SmartPtr<Ipopt::Journalist> journalist,
00052     const std::string & prefix):
00053     journalist_(journalist),
00054     options_(options),
00055     roptions_(roptions),
00056     prefix_(prefix),
00057     start_time_(0),
00058     time_limit_(DBL_MAX)
00059   {
00060   }
00061 
00062   TNLPSolver::TNLPSolver(const TNLPSolver &other):
00063     journalist_(other.journalist_),
00064     options_(NULL),
00065     roptions_(other.roptions_),
00066     prefix_(other.prefix_),
00067     start_time_(other.start_time_),
00068     time_limit_(other.time_limit_){
00069       options_ = new Ipopt::OptionsList();
00070       *options_ = *other.options_;
00071   }
00072   
00073   TNLPSolver::~TNLPSolver()
00074   {}
00075 
00076 
00077   bool
00078   TNLPSolver::zeroDimension(const Ipopt::SmartPtr<Ipopt::TNLP>& tnlp, ReturnStatus &optimizationStatus)
00079   {
00080 
00081     int n,m,dum1, dum2;
00082     Ipopt::TNLP::IndexStyleEnum dum3;
00083     tnlp->get_nlp_info(n,m,dum1, dum2, dum3);
00084     double * x_l = new double[n];
00085     double * x_u = new double[n];
00086    
00087     double * g_l = (m>0) ? new double[m] : NULL;
00088     double * g_u = (m >0) ? new double[m] : NULL;
00089     
00090     tnlp->get_bounds_info(n, x_l, x_u, m, g_l , g_u);
00091     
00092 
00093     for(int i = 0 ; i < n ; i++) {
00094       if(x_u[i] - x_l[i] > 1e-5)
00095         {
00096           delete [] x_l;
00097           delete [] x_u;
00098           if(m > 0){
00099             delete [] g_l;
00100             delete [] g_u;
00101           }
00102           return 0;
00103         }
00104     }
00105 
00106     //Problem has no variables just check if the unique solution given by the bounds is
00107     // feasible or not.
00108     double obj_value;
00109 
00110     tnlp->eval_f(n, x_l, true, obj_value);
00111 
00112     double * x_sol = new double[n];
00113 
00114       
00115     IpBlasDcopy(n, x_l, 1, x_sol, 1);
00116 
00117     delete [] x_l;
00118     delete [] x_u;
00119 
00120     double * g_sol = (m > 0) ? new double [m] : NULL;
00121 
00122     tnlp->eval_g(n, x_sol, true, m, g_sol);
00123     
00124     optimizationStatus = solvedOptimal;
00125     for(int i = 0 ; i < m ; i++) {
00126       if(g_sol[i] - g_l[i] <  - 1e-07 || g_sol[i] - g_u[i] > 1e-07) {
00127         optimizationStatus = provenInfeasible;
00128         
00129         delete [] g_l;
00130         delete [] g_u;
00131         double * lam = (m > 0) ? new double[m]: NULL;
00132         CoinFillN(lam,m,0.);
00133         double * z = new double[n];
00134         CoinFillN(z,n,0.);
00135         tnlp->finalize_solution(Ipopt::LOCAL_INFEASIBILITY,
00136                                n, x_sol, NULL, NULL, 
00137                                m, g_sol, NULL, obj_value, NULL, NULL);
00138         if (m > 0) delete [] lam;
00139         delete [] z;
00140         if (m > 0) delete [] g_sol;
00141         delete [] x_sol;
00142 
00143         return 1;
00144       }
00145     }
00146     if (m > 0) delete [] g_l;
00147     if (m > 0) delete [] g_u;
00148 
00149     double * lam = (m > 0) ? new double[m] : NULL;
00150     CoinFillN(lam,m,0.);
00151     double * z = new double[n];
00152     CoinFillN(z,n,0.);
00153     tnlp->finalize_solution(Ipopt::SUCCESS,
00154                            n, x_sol, z, z,
00155                            m, g_sol, lam, obj_value, NULL, NULL);
00156     if (m > 0) delete [] lam;
00157     delete [] z;
00158     if (m > 0) delete [] g_sol;
00159     delete [] x_sol;
00160     return 1;
00161   }
00162 
00163 void
00164 TNLPSolver::UnsolvedError::printError(std::ostream &os)
00165 {
00166   os<<solverName()<<" exited with error code "<<errorNum_<<" "<<errorName()<<std::endl;
00167 }
00168 
00169 void
00170 TNLPSolver::UnsolvedError::writeDiffFiles(const std::string prefix) const{
00171   const int numcols = model_->num_variables();
00172   const int numrows = model_->num_constraints();
00173   
00174   const double * currentLower = model_->x_l();
00175   const double * currentUpper = model_->x_u();
00176 
00177   const double * originalLower = model_->orig_x_l();
00178   const double * originalUpper = model_->orig_x_u();
00179   CoinRelFltEq eq;
00180   std::string fBoundsName = prefix + name_;
00181   fBoundsName+="_bounds";
00182   
00183   std::string fModName = fBoundsName + ".mod";
00184   std::ofstream fBounds;
00185   std::ofstream fMod;
00186 
00188   bool hasVarNames = 0;
00189   NamesReader reader(name_,".col");
00190   
00191   if(reader.readFile())
00192       hasVarNames=1;
00193   if(hasVarNames)
00194     fMod.open(fModName.c_str());
00195   fBounds.open(fBoundsName.c_str());
00196     
00197   for(int i = 0 ; i < numcols ; i++)
00198     {    
00199     if(!eq(currentLower[i],originalLower[i]))
00200       {
00201         if(hasVarNames)
00202           fMod<<"bounds"<<i<<": "
00203               <<reader.name(i)<<" >= "
00204               <<currentLower[i]<<";\n";
00205 
00206 
00207         fBounds<<"LO"<<"\t"<<i<<"\t"<<currentLower[i]<<std::endl;
00208     }
00209     if(!eq(currentUpper[i],originalUpper[i]))
00210       {
00211         if(hasVarNames)
00212           fMod<<"bounds"<<i<<": "
00213               <<reader.name(i)<<" <= "
00214               <<currentUpper[i]<<";\n";
00215         
00216         fBounds<<"UP"<<"\t"<<i<<"\t"<<currentUpper[i]<<std::endl;
00217       }
00218     }
00219   
00220     //write a file with starting point
00221     std::string fStartPointName = name_;
00222     fStartPointName+="_start";
00223 
00224 
00225 
00226     const double * primals = model_->x_init();
00227     const double * duals = model_->duals_init();
00228 
00229     if(!primals)//No starting point no output
00230       {
00231         std::cerr<<"A failure has occured but no starting point exists"<<std::endl;
00232         return;
00233       }
00234 
00235     std::ofstream fStartPoint(fStartPointName.c_str());
00236     fStartPoint.precision(17);
00237     fStartPoint<<numcols<<"\t"<<2*numcols+numrows<<std::endl;
00238     for(int i = 0 ; i < numcols ; i++)
00239     fStartPoint<<primals[i]<<std::endl;
00240     int end = 2*numcols + numrows;
00241     if(duals)
00242       {
00243         for(int i = 0 ; i < end; i++)
00244           fStartPoint<<duals[i]<<std::endl;
00245       }
00246 
00247  
00248 }
00249 
00252   bool 
00253   TNLPSolver::isRecoverable(ReturnStatus &r){
00254     return (r >=0 || (r != illDefinedProblem && r != illegalOption && r != computationError && r != timeLimit) );
00255   }
00256 
00258 void 
00259 TNLPSolver::initializeOptionsAndJournalist(){
00260   prefix_ = "bonmin.";
00261   options_ = new Ipopt::OptionsList();
00262   
00263   journalist_= new Ipopt::Journalist();
00264   roptions_ = new Bonmin::RegisteredOptions();
00265   
00266   try{
00267     Ipopt::SmartPtr<Ipopt::Journal> stdout_journal =
00268     journalist_->AddFileJournal("console", "stdout", Ipopt::J_ITERSUMMARY);
00269     
00270     options_->SetJournalist(journalist_);
00271     options_->SetRegisteredOptions(GetRawPtr(roptions_));
00272   }
00273   catch (Ipopt::IpoptException &E){
00274     E.ReportException(*journalist_);
00275     throw E;
00276   }
00277   catch(std::bad_alloc){
00278     journalist_->Printf(Ipopt::J_ERROR, Ipopt::J_MAIN, "\n Not enough memory .... EXIT\n");
00279     throw -1;
00280   }
00281   catch(...){
00282     Ipopt::IpoptException E("Uncaught exception in FilterSolver::FilterSolver()",
00283                             "BonFilterSolver.cpp",-1);
00284     throw E;
00285   }
00286   
00287 }
00288 
00289 
00290 }//end namespace Bonmin
00291 

Generated on Thu Nov 10 03:05:42 2011 by  doxygen 1.4.7