double CEquiEnergy_TState::HillClimb_CSMINWEL(size_t nSolution) { energy_level = parameter->number_energy_level; bool if_bounded_old = if_bounded; if_bounded = false; MinusLogPosterior_CSMINWEL::model = this; int n = current_sample.data.dim; double *H=new double[n*n], *g=new double[n], *x=new double[n], crit = 1.0e-3, fh; int nit=50, itct, fcount; int retcodeh; const double IniHCsminwel=1.0e-5; double max_log_posterior = -1.0e300; for (int iSolution=0; iSolution < nSolution; iSolution ++) { InitializeParameter(x, n); for (int i=0; i<n; i++) for (int j=0; j<n; j++) H[i*n+j] = IniHCsminwel; for (int i=0; i<n; i++) g[i] = 0.0; dw_csminwel(MinusLogPosterior_CSMINWEL::function, x, n, H, g, NULL, &fh, crit, &itct, nit, &fcount, &retcodeh, NULL, NULL); if (retcodeh == 0) { CSampleIDWeight sample; sample.data.Resize(n); for (int i=0; i<n; i++) sample.data[i] = x[i]; sample.DataChanged(); sample.id = (int)(time(NULL)-timer_when_started); log_posterior_function(sample); SaveSampleToStorage(sample); max_log_posterior = sample.weight > max_log_posterior ? sample.weight : max_log_posterior; } } delete []x; delete []g; delete []H; storage->finalize(energy_level); storage->ClearDepositDrawHistory(energy_level); if_bounded = if_bounded_old; return max_log_posterior; }
//------------------------------------------------------------------------------ // bool Initialize(ObjectMap *objectMap, ObjectMap *globalObjectMap) //------------------------------------------------------------------------------ bool MathTree::Initialize(ObjectMap *objectMap, ObjectMap *globalObjectMap) { if (theTopNode == NULL) { #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::Initialize() theTopNode is NULL, so just returning true\n"); #endif return true; } theObjectMap = objectMap; theGlobalObjectMap = globalObjectMap; #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::Initialize() theTopNode=%s, %s\n", theTopNode->GetTypeName().c_str(), theTopNode->GetName().c_str()); #endif return InitializeParameter(theTopNode); }
//------------------------------------------------------------------------------ // bool InitializeParameter(MathNode *node) //------------------------------------------------------------------------------ bool MathTree::InitializeParameter(MathNode *node) { if (node == NULL) { #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() theTopNode is NULL, so just returning true\n"); #endif return true; } #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() node=%s, %s\n IsFunction=%d, IsNumber=%d, " "IsFunctionInput=%d\n", node->GetTypeName().c_str(), node->GetName().c_str(), node->IsFunction(), node->IsNumber(), node->IsFunctionInput()); #endif if (!node->IsFunction()) { if (node->IsNumber()) return true; if (node->IsFunctionInput()) return true; // Now MathElement can have more than one ref objects due to GmatFunction // input arguments. StringArray refNames = node->GetRefObjectNameArray(Gmat::PARAMETER); std::string undefNames; for (UnsignedInt i=0; i<refNames.size(); i++) { #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() refNames[%d]=%s\n", i, refNames[i].c_str()); #endif // Handle array index Integer row, col; std::string newName; GmatStringUtil::GetArrayIndex(refNames[i], row, col, newName); if (theObjectMap->find(newName) != theObjectMap->end()) { node->SetRefObject((*theObjectMap)[newName], Gmat::PARAMETER, newName); #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() Found %s from theObjectMap\n", refNames[i].c_str()); #endif } else if (theGlobalObjectMap->find(newName) != theGlobalObjectMap->end()) { node->SetRefObject((*theGlobalObjectMap)[newName], Gmat::PARAMETER, newName); #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() Found %s from theGlobalObjectMap\n", refNames[i].c_str()); #endif } else { #ifdef DEBUG_MATH_TREE_INIT MessageInterface::ShowMessage ("MathTree::InitializeParameter() Unable to find " + newName + " from theObjectMap or theGlobalObjectMap\n"); #endif undefNames = undefNames + ", " + newName; } } if (undefNames == "") return true; else throw InterpreterException("Undefined variable(s) \"" + undefNames + "\" used in MathTree"); } else { MathNode *left = node->GetLeft(); bool result1 = InitializeParameter(left); MathNode *right = node->GetRight(); bool result2 = InitializeParameter(right); return (result1 && result2); } }
// HillClimb is always one on the original model. Therefore, if_bounded will be set as false temperoraly // so that all calculation can be perfomed on the original model. After HillClimb is finished, if_bounded // will be set as its original value. // Samples generated during HillClimb will be saved into storage but always at the level of number_energy_level // (the extra level) double CEquiEnergy_TState::HillClimb_NPSOL(size_t nSolution ) { energy_level = parameter->number_energy_level; bool if_bounded_old = if_bounded; if_bounded = false; // temperarily set if_bounded as false so all calculation is done on original model const string COLD_START = string("Cold Start"); const string NO_PRINT_OUT = string("Major print level = 0"); const string DERIVATIVE_LEVEL = string("Derivative level = 0"); // npsol MinusLogPosterior_NPSOL::model = this; int n = current_sample.data.dim; // sample dimension // linear constraints int nclin = 0; // number of linear constraints int ldA = nclin > 1 ? nclin : 1; // number of rows of A double *A = new double[ldA*n]; // nonlinear constraints int ncnln = 0; // number of nonlinear constraints int ldJ = ncnln > 1 ? ncnln : 1; // number of rows of cJac; double *cJac = new double[ldJ*n]; // R provides the upper-triangular Cholesky factor of the initial approximation // of the Hessian of the Lagrangian int ldR = n; // number of rows of R; double *R = new double[ldR*n]; // int nctotal = n + nclin + ncnln; int *istate = new int[nctotal]; // array indicating whether the constaits are effective double *bl = new double[nctotal]; // lower bounds for samples, A and cJac double *bu = new double[nctotal]; // upper bounds for samples, A and cJac for (int i=0; i<n; i++) { bl[i] = 0.0; bu[i] = 100.0; } double *clambda = new double [nctotal]; // lagragin parameters of the constraints for (int i=0; i<nctotal; i++) clambda[i] = 0; // work space int leniw = 3*n + nclin + 2*ncnln; int *iw = new int [leniw]; // integer work space int lenw; if (nclin == 0 && ncnln == 0) lenw = 20*n; else if (ncnln == 0) lenw = 2*n*n + 20*n + 11*nclin; else lenw = 2*n*n + n*nclin + 2*n*ncnln + 20*n + 11*nclin + 21*ncnln; double *w = new double[lenw]; // floating work space // initial estimate of the solution double *x = new double[n]; // returning value of npsol int inform, iter; double *c = new double[1]; // because ncnln = 0 double f; // value of objective f(x) at the final iterate double *g = new double[n]; // objective gradient double max_log_posterior = -1.0e300; npoptn_((char*)DERIVATIVE_LEVEL.c_str(), DERIVATIVE_LEVEL.length()); // npoptn_((char*)NO_PRINT_OUT.c_str(), NO_PRINT_OUT.length()); // test if LogPosterior_StatesIntegratedOut works for (int i=0; i<nSolution; i++) { InitializeParameter(x, n); npoptn_((char*)COLD_START.c_str(), COLD_START.length()); npsol_(&n, &nclin, &ncnln, &ldA, &ldJ, &ldR, A, bl, bu, NULL, MinusLogPosterior_NPSOL::function, &inform, &iter, istate, c, cJac, clambda, &f, g, R, x, iw, &leniw, w, &lenw); if (f < 1.0e300) { CSampleIDWeight sample; sample.data.Resize(n); for (int j=0; j<n; j++) sample.data[j] = x[j]; sample.DataChanged(); sample.id = (int)(time(NULL)-timer_when_started); log_posterior_function(sample); SaveSampleToStorage(sample); max_log_posterior = sample.weight > max_log_posterior ? sample.weight : max_log_posterior; } } delete [] g; delete [] c; delete [] w; delete [] iw; delete [] istate; delete [] clambda; delete [] bu; delete [] bl; delete [] R; delete [] cJac; delete [] A; storage->finalize(energy_level); storage->ClearDepositDrawHistory(energy_level); if_bounded = if_bounded_old; return max_log_posterior; }