CFactorGraph CompressInterface::createCFactorGraph() { createVarClustering(); createFacClustering(); // create lifted fg here vector<CFactor> superFacs; // clusterIdx => facIdx for (map<size_t,size_t>::iterator facIter = _facRepr.begin(); facIter != _facRepr.end(); facIter++) { VarSet superVarSet; foreach (const dai::BipartiteGraph::Neighbor &tmpVar, _cfg.nbF(facIter->second)) { Var varCluster = _varRepr[_varColorVec[tmpVar]]; if (!superVarSet.contains(varCluster)) { superVarSet |= Var(varCluster); } } CFactor superFac = CFactor(superVarSet, _cfg.factor(facIter->second).p()); superFac.sigma() = _cfg.factor(facIter->second).sigma(); superFac.position() = _cfg.factor(facIter->second).position(); superFac.counts() = createCounts(facIter->second, superVarSet); superFacs.push_back(superFac); } return CFactorGraph(superFacs); }
void CLWSamplingInfEngine:: EnterEvidence( const CEvidence *pEvidenceIn , int maximize , int sumOnMixtureNode ) { PNL_CHECK_IS_NULL_POINTER(pEvidenceIn); LWSampling(pEvidenceIn); // Given evidencs, calculate particle weight by CPD float w; int iSampleSize = m_currentEvVec.size(); const int* ObsNodes = pEvidenceIn->GetAllObsNodes(); int NumberObsNodes = pEvidenceIn->GetNumberObsNodes(); int i, j; for( i = 0; i < iSampleSize; i++) { w = 0; for( j = 0; j < NumberObsNodes; j++) { if(pEvidenceIn->IsNodeObserved(ObsNodes[j])) { CFactor* pFactor = m_pGraphicalModel->GetFactor(ObsNodes[j]); w = w + pFactor->GetLogLik( m_currentEvVec[i]); } } m_particleWeight[i] = (float)exp(w); } NormalizeWeight(); }
void CFactorGraph::compute_energies() { for (int32_t fi = 0; fi < m_factors->get_num_elements(); ++fi) { CFactor* fac = dynamic_cast<CFactor*>(m_factors->get_element(fi)); fac->compute_energies(); SG_UNREF(fac); } }
void CFactorGraph::loss_augmentation(SGVector<int32_t> states_gt, SGVector<float64_t> loss) { if (loss.size() == 0) { loss.resize_vector(states_gt.size()); SGVector<float64_t>::fill_vector(loss.vector, loss.vlen, 1.0 / states_gt.size()); } int32_t num_vars = states_gt.size(); ASSERT(num_vars == loss.size()); SGVector<int32_t> var_flags(num_vars); var_flags.zero(); // augment loss to incorrect states in the first factor containing the variable // since += L_i for each variable if it takes wrong state ever // TODO: augment unary factors for (int32_t fi = 0; fi < m_factors->get_num_elements(); ++fi) { CFactor* fac = dynamic_cast<CFactor*>(m_factors->get_element(fi)); SGVector<int32_t> vars = fac->get_variables(); for (int32_t vi = 0; vi < vars.size(); vi++) { int32_t vv = vars[vi]; ASSERT(vv < num_vars); if (var_flags[vv]) continue; SGVector<float64_t> energies = fac->get_energies(); for (int32_t ei = 0; ei < energies.size(); ei++) { CTableFactorType* ftype = fac->get_factor_type(); int32_t vstate = ftype->state_from_index(ei, vi); SG_UNREF(ftype); if (states_gt[vv] == vstate) continue; // -delta(y_n, y_i_n) fac->set_energy(ei, energies[ei] - loss[vv]); } var_flags[vv] = 1; } SG_UNREF(fac); } // make sure all variables have been checked int32_t min_var = SGVector<int32_t>::min(var_flags.vector, var_flags.vlen); ASSERT(min_var == 1); }
float64_t CFactorGraph::evaluate_energy(const SGVector<int32_t> state) const { ASSERT(state.size() == m_cardinalities.size()); float64_t energy = 0.0; for (int32_t fi = 0; fi < m_factors->get_num_elements(); ++fi) { CFactor* fac = dynamic_cast<CFactor*>(m_factors->get_element(fi)); energy += fac->evaluate_energy(state); SG_UNREF(fac); } return energy; }
void CompressInterface::rearrangeCnfFactor(CFactor &cnfClause) { State state(cnfClause.vars()); vector<size_t> (cnfClause.vars().size()); vector<size_t> pos,neg,sigma; for (size_t i=0; i<cnfClause.states(); i++) { if (cnfClause[i] == 1) { for (vector<Var>::const_iterator varIter=cnfClause.vars().begin(); varIter!=cnfClause.vars().end();varIter++) { if (state(*varIter) == 0) { pos.push_back(varIter - cnfClause.vars().begin()); } else { neg.push_back(varIter - cnfClause.vars().begin()); } } break; } else if (cnfClause[i] == 0) { //TODO handle factors which contain zero states // in such cases the possible zero state could have been clamped; // possible solutions: // i) restore factor from backup (requires to clamp factors accordingly) // ii) cache zero states in advance return; } state++; } sigma.insert(sigma.begin(),pos.begin(), pos.end()); sigma.insert(sigma.begin() + pos.size(),neg.begin(), neg.end()); cnfClause.sigma() = sigma; }
void CBayesLearningEngine::Learn() { if(!m_pGrModel) { PNL_THROW( CNULLPointer, "no graphical model") } CStaticGraphicalModel *grmodel = this->GetStaticModel(); CFactor *factor = NULL; int numberOfFactors = grmodel->GetNumberOfFactors(); int domainNodes; if(m_numberOfLearnedEvidences == m_numberOfAllEvidences) { PNL_THROW(COutOfRange, "number of unlearned evidences must be positive") } int currentEvidNumber; const CEvidence* pCurrentEvid; //below code is intended to work on tabular CPD and gaussian CPD //later we will generalize it for other distribution types if ((grmodel->GetFactor(0))->GetDistributionType() == dtTabular) { for( int ev = m_numberOfLearnedEvidences; ev < m_numberOfAllEvidences; ev++) { currentEvidNumber = ev; pCurrentEvid = m_Vector_pEvidences[currentEvidNumber]; if( !pCurrentEvid) { PNL_THROW(CNULLPointer, "evidence") } for( domainNodes = 0; domainNodes < numberOfFactors; domainNodes++ ) { factor = grmodel->GetFactor( domainNodes ); int DomainSize; const int *domain; factor->GetDomain( &DomainSize, &domain ); const CEvidence *pEvidences[] = { pCurrentEvid }; CTabularDistribFun* pDistribFun = (CTabularDistribFun*)(factor->GetDistribFun()); pDistribFun->BayesUpdateFactor(pEvidences, 1, domain); } } } else { for( domainNodes = 0; domainNodes < numberOfFactors; domainNodes++ )
SGVector< float64_t > CFactorGraphModel::get_joint_feature_vector(int32_t feat_idx, CStructuredData* y) { // factor graph instance CFactorGraphFeatures* mf = CFactorGraphFeatures::obtain_from_generic(m_features); CFactorGraph* fg = mf->get_sample(feat_idx); // ground truth states CFactorGraphObservation* fg_states = CFactorGraphObservation::obtain_from_generic(y); SGVector<int32_t> states = fg_states->get_data(); // initialize psi SGVector<float64_t> psi(get_dim()); psi.zero(); // construct unnormalized psi CDynamicObjectArray* facs = fg->get_factors(); for (int32_t fi = 0; fi < facs->get_num_elements(); ++fi) { CFactor* fac = dynamic_cast<CFactor*>(facs->get_element(fi)); CTableFactorType* ftype = fac->get_factor_type(); int32_t id = ftype->get_type_id(); SGVector<int32_t> w_map = get_params_mapping(id); ASSERT(w_map.size() == ftype->get_w_dim()); SGVector<float64_t> dat = fac->get_data(); int32_t dat_size = dat.size(); ASSERT(w_map.size() == dat_size * ftype->get_num_assignments()); int32_t ei = ftype->index_from_universe_assignment(states, fac->get_variables()); for (int32_t di = 0; di < dat_size; di++) psi[w_map[ei*dat_size + di]] += dat[di]; SG_UNREF(ftype); SG_UNREF(fac); } // negation (-E(x,y) = <w,phi(x,y)>) psi.scale(-1.0); SG_UNREF(facs); SG_UNREF(fg); return psi; }
CMNet* CMNet::CreateWithRandomMatrices( const intVecVector& clqs, CModelDomain* pMD) { CMNet* pMNet = CMNet::Create( clqs, pMD ); pMNet->AllocFactors(); int numFactors = pMNet->GetNumberOfFactors(); int i; for( i = 0; i < numFactors; i++ ) { pMNet->AllocFactor( i ); CFactor* ft = pMNet->GetFactor(i); ft->CreateAllNecessaryMatrices(); } return pMNet; }
void cfactor_setitem(CFactor& factor, size_t index, double value) { if (index >= 0 && index < factor.states()) { factor[index] = value; } else { PyErr_SetString(PyExc_IndexError, "index out of range"); boost::python::throw_error_already_set(); } }
//create mnet with random matrices CMRF2* CMRF2::CreateWithRandomMatrices( int numberOfCliques, const int *cliqueSizes, const int **cliques, CModelDomain* pMD) { CMRF2* pMRF2 = CMRF2::Create( numberOfCliques, cliqueSizes, cliques, pMD ); pMRF2->AllocFactors(); int numFactors = pMRF2->GetNumberOfFactors(); int i; for( i = 0; i < numFactors; i++ ) { pMRF2->AllocFactor( i ); CFactor* ft = pMRF2->GetFactor(i); ft->CreateAllNecessaryMatrices(); } return pMRF2; }
void CMlLearningEngine::Learn() { /* function takes an information from m_pEvidences and learns factors of graphical model using prior probabilities or not */ float logLikTmp = 0; if(!m_pGrModel) { PNL_THROW( CNULLPointer, "no graphical model") } CStaticGraphicalModel *grmodel = this->GetStaticModel(); CFactor *parameter = NULL; int numberOfDomains = grmodel -> GetNumberOfFactors(); for( int domainNodes = 0; domainNodes < numberOfDomains; domainNodes++ ) { factor = grmodel->GetFactor( domainNodes ); factor ->UpdateStatisticsML( &m_Vector_pEvidences.front(), m_Vector_pEvidences.size() ); PNL_CHECK_LEFT_BORDER(m_numberOfAllEvidences, 1); logLikTmp += parameter->ProcessingStatisticalData(m_numberOfAllEvidences); } switch( grmodel -> GetModelType() ) { case mtBNet: { break; } case mtMRF2: case mtMNet: { logLikTmp = _LearnPotentials(); break; } default: { PNL_THROW(CBadConst, "model type" ) break; } } m_critValue.push_back(logLikTmp); }
double cfactor_getitem(CFactor &factor, size_t index) { if (index >= 0 && index < factor.states()) { return factor[index]; } else { PyErr_SetString(PyExc_IndexError, "index out of range"); boost::python::throw_error_already_set(); return -1; } }
CCPD* CStaticStructLearnSEM::CreateRandomCPD(int nfamily, const int* family, CBNet* pBNet) { int child = family[nfamily-1]; CModelDomain* pMD = pBNet->GetModelDomain(); CFactor* factor = pBNet->GetFactor(child); EDistributionType dt = factor->GetDistributionType(); CCPD* pCPD; if( dt == dtTabular ) { pCPD = CTabularCPD::Create(family, nfamily, pMD); pCPD->CreateAllNecessaryMatrices(1); return pCPD; } else { if( dt == dtMixGaussian ) { floatVector data; static_cast<CMixtureGaussianCPD*>(factor)->GetProbabilities(&data); pCPD = CMixtureGaussianCPD::Create(family, nfamily, pMD, &data.front()); static_cast<CCondGaussianDistribFun*>(pCPD->GetDistribFun()) -> CreateDefaultMatrices(1); return pCPD; } else { if( (dt == dtGaussian) || (dt == dtCondGaussian) ) { pCPD = CGaussianCPD::Create(family, nfamily, pMD); pCPD->CreateAllNecessaryMatrices(1); return pCPD; } else PNL_THROW(CNotImplemented, "this type of distribution is not supported yet"); } } }
void CFactorGraph::connect_components() { if (m_dset->get_connected()) return; // need to be reset once factor graph is updated m_dset->make_sets(); bool flag = false; for (int32_t fi = 0; fi < m_factors->get_num_elements(); ++fi) { CFactor* fac = dynamic_cast<CFactor*>(m_factors->get_element(fi)); SGVector<int32_t> vars = fac->get_variables(); int32_t r0 = m_dset->find_set(vars[0]); for (int32_t vi = 1; vi < vars.size(); vi++) { // for two nodes in a factor, should be an edge between them // but this time link() isn't performed, if they are linked already // means there is another path connected them, so cycle detected int32_t ri = m_dset->find_set(vars[vi]); if (r0 == ri) { flag = true; continue; } r0 = m_dset->link_set(r0, ri); } SG_UNREF(fac); } m_has_cycle = flag; m_dset->set_connected(true); }
void CParEMLearningEngine::LearnOMP() { CStaticGraphicalModel *pGrModel = this->GetStaticModel(); PNL_CHECK_IS_NULL_POINTER(pGrModel); PNL_CHECK_LEFT_BORDER(GetNumEv() - GetNumberProcEv() , 1); //omp_set_num_threads(2); int numberOfThreads = omp_get_num_procs(); //CParPearlInfEngine **pCurrentInfEng = new CParPearlInfEngine*[numberOfThreads]; CJtreeInfEngine **pCurrentInfEng = new CJtreeInfEngine*[numberOfThreads]; for (int i = 0; i < numberOfThreads; i++) pCurrentInfEng[i] = NULL; CFactor *parameter1 = NULL; int exit = 0; int numberOfParameters = pGrModel->GetNumberOfParameters(); int domainNodes; //int itsML = 0; // !!! float loglik = -FLT_MAX; float loglikOld = -FLT_MAX; float epsilon = GetPrecisionEM(); float stopExpression = epsilon + 1.0f; int iteration = 0; int ev; // to create additional factors CFactor **ppAllFactors = new CFactor*[numberOfParameters*numberOfThreads]; bool *was_updated = new bool[numberOfParameters*numberOfThreads]; int factor; #pragma omp parallel for private(factor) default(shared) for (factor = 0; factor < numberOfParameters; factor++) { ppAllFactors[factor] = pGrModel->GetFactor(factor); ppAllFactors[factor]->GetDistribFun()->ClearStatisticalData(); was_updated[factor] = false; for (int proc = 1; proc < numberOfThreads; proc++) { ppAllFactors[factor + proc * numberOfParameters] = ppAllFactors[factor]->Clone(); ppAllFactors[factor + proc * numberOfParameters]->GetDistribFun()-> ClearStatisticalData(); was_updated[factor + proc * numberOfParameters]= false; }; }; int* itsML = new int[numberOfThreads]; for (int delta = 0; delta < numberOfThreads; delta++) { itsML[delta] = 0; }; int start_ev, end_ev; do { iteration++; start_ev = GetNumberProcEv(); end_ev = GetNumEv(); #pragma omp parallel for schedule(dynamic) private(ev) for (ev = start_ev; ev < end_ev ; ev++) { CFactor *parameter = NULL; int DomainNodes_new; int bMaximize = 0; int bSumOnMixtureNode = 0; int infIsNeed = 0; int currentEvidNumber = ev; // !!! const CEvidence* pCurrentEvid = m_Vector_pEvidences[currentEvidNumber]; infIsNeed = !GetObsFlags(ev)->empty(); // !!! int Num_thread = omp_get_thread_num(); if (infIsNeed) { if (!pCurrentInfEng[Num_thread]) { pCurrentInfEng[Num_thread] = CJtreeInfEngine::Create( (const CStaticGraphicalModel *)pGrModel); } pCurrentInfEng[Num_thread]->EnterEvidence(pCurrentEvid, bMaximize, bSumOnMixtureNode); } for (DomainNodes_new = 0; DomainNodes_new < numberOfParameters; DomainNodes_new++) { parameter = ppAllFactors[DomainNodes_new + Num_thread * numberOfParameters]; if (infIsNeed) { int DomainSize; const int *domain; parameter->GetDomain(&DomainSize, &domain); if (IsDomainObserved(DomainSize, domain, currentEvidNumber)) { const CEvidence *pEvidences[] = { pCurrentEvid }; parameter->UpdateStatisticsML(pEvidences, 1); was_updated[DomainNodes_new+Num_thread*numberOfParameters]= true; } else { pCurrentInfEng[Num_thread]->MarginalNodes(domain, DomainSize, 1); const CPotential * pMargPot = pCurrentInfEng[Num_thread]->GetQueryJPD(); parameter ->UpdateStatisticsEM(pMargPot, pCurrentEvid); was_updated[DomainNodes_new+Num_thread*numberOfParameters]= true; } } else { const CEvidence *pEvidences[] = { pCurrentEvid }; parameter->UpdateStatisticsML(pEvidences, 1); was_updated[DomainNodes_new+Num_thread*numberOfParameters]= true; } } itsML[Num_thread] = itsML[Num_thread] || !infIsNeed; } // end of parallel for for (int delta = 1; delta < numberOfThreads; delta++) { itsML[0] = itsML[0] || itsML[delta]; }; //to join factors #pragma omp parallel for private(factor) default(shared) for (factor = 0; factor < numberOfParameters; factor++) { for (int proc = 1; proc < numberOfThreads; proc++) { if (was_updated[factor+proc*numberOfParameters]) { ppAllFactors[factor]->UpdateStatisticsML(ppAllFactors[factor + proc*numberOfParameters]); ppAllFactors[factor+proc*numberOfParameters]->GetDistribFun()-> ClearStatisticalData(); }; was_updated[factor+proc*numberOfParameters] = false; }; }; switch (pGrModel->GetModelType()) { case mtBNet: { loglikOld = loglik; loglik = 0.0f; for (domainNodes = 0; domainNodes < numberOfParameters; domainNodes++) { parameter1 = pGrModel->GetFactor(domainNodes); loglik += parameter1->ProcessingStatisticalData( m_numberOfAllEvidences); } break; } case mtMRF2: case mtMNet: { loglikOld = loglik; loglik = _LearnPotentials(); break; } default: { PNL_THROW(CBadConst, "model type") break; } } stopExpression = float(fabs(2 * (loglikOld - loglik) / (loglikOld + loglik))); exit = ((stopExpression > epsilon) && (iteration <= GetMaxIterEM())) && !itsML[0]; if (exit) { ClearStatisticData(); } m_critValue.push_back(loglik); for (int j = 0; j < numberOfThreads; j++) { delete pCurrentInfEng[j]; pCurrentInfEng[j] = NULL; } } while (exit); delete [] pCurrentInfEng; //”даление дополнительных факторов for (factor = numberOfParameters; factor < numberOfParameters * numberOfThreads; factor++) { delete ppAllFactors[factor]; }; delete[] ppAllFactors; delete[] was_updated; if (iteration > GetMaxIterEM()) { PNL_THROW(CNotConverged, "maximum number of iterations") } SetNumProcEv( GetNumEv() ); }
void CParEMLearningEngine::Learn() { CStaticGraphicalModel *pGrModel = this->GetStaticModel(); PNL_CHECK_IS_NULL_POINTER(pGrModel); PNL_CHECK_LEFT_BORDER(GetNumEv() - GetNumberProcEv() , 1); CJtreeInfEngine *pCurrentInfEng = NULL; CFactor *parameter = NULL; int exit = 0; int numberOfParameters = pGrModel->GetNumberOfParameters(); int domainNodes; int infIsNeed = 0; int itsML = 0; // !!! float loglik = -FLT_MAX; float loglikOld = -FLT_MAX; float epsilon = GetPrecisionEM(); float stopExpression = epsilon + 1.0f; int iteration = 0; int currentEvidNumber; int bMaximize = 0; int bSumOnMixtureNode = 0; const CEvidence* pCurrentEvid; int start_mpi, finish_mpi; int NumberOfProcesses, MyRank; int numSelfEvidences; MPI_Comm_size(MPI_COMM_WORLD, &NumberOfProcesses); MPI_Comm_rank(MPI_COMM_WORLD, &MyRank); int d = 0; do { iteration++; numSelfEvidences = (GetNumEv() - GetNumberProcEv()) / NumberOfProcesses; start_mpi = GetNumberProcEv() + numSelfEvidences * MyRank; // !!! if (MyRank < NumberOfProcesses - 1) finish_mpi = start_mpi + numSelfEvidences; // !!! else finish_mpi = GetNumEv(); // !!! for(int ev = start_mpi; ev < finish_mpi; ev++) { infIsNeed = 0; currentEvidNumber = ev; // !!! pCurrentEvid = m_Vector_pEvidences[currentEvidNumber]; if( !pCurrentEvid) { PNL_THROW(CNULLPointer, "evidence") } infIsNeed = !GetObsFlags(ev)->empty(); // !!! if(infIsNeed) { // create inference engine if(!pCurrentInfEng) { pCurrentInfEng = CJtreeInfEngine::Create(pGrModel); } pCurrentInfEng->EnterEvidence(pCurrentEvid, bMaximize, bSumOnMixtureNode); } for(domainNodes = 0; domainNodes < numberOfParameters; domainNodes++) { parameter = pGrModel->GetFactor(domainNodes); if(infIsNeed) { int DomainSize; const int *domain; parameter->GetDomain(&DomainSize, &domain); if (IsDomainObserved(DomainSize, domain, currentEvidNumber)) { const CEvidence *pEvidences[] = { pCurrentEvid }; parameter->UpdateStatisticsML(pEvidences, 1); } else { pCurrentInfEng->MarginalNodes(domain, DomainSize, 1); const CPotential * pMargPot = pCurrentInfEng->GetQueryJPD(); parameter ->UpdateStatisticsEM(pMargPot, pCurrentEvid); } } else { const CEvidence *pEvidences[] = { pCurrentEvid }; parameter->UpdateStatisticsML(pEvidences, 1); } } itsML = itsML || !infIsNeed; } for(domainNodes = 0; domainNodes < numberOfParameters; domainNodes++ ) { parameter = pGrModel->GetFactor(domainNodes); CNumericDenseMatrix<float> *matForSending; int matDim; const int *pMatRanges; int dataLength; const float *pDataForSending; matForSending = static_cast<CNumericDenseMatrix<float>*> ((parameter->GetDistribFun())->GetStatisticalMatrix(stMatTable)); matForSending->GetRanges(&matDim, &pMatRanges); matForSending->GetRawData(&dataLength, &pDataForSending); float *pDataRecv = new float[dataLength]; float *pDataRecv_copy = new float[dataLength]; MPI_Status status; MPI_Allreduce((void*)pDataForSending, pDataRecv, dataLength, MPI_FLOAT, MPI_SUM, MPI_COMM_WORLD); CNumericDenseMatrix<float> *RecvMatrix = static_cast<CNumericDenseMatrix<float>*> (parameter->GetDistribFun()->GetStatisticalMatrix(stMatTable)); int dataLength_new; float *pData_new; RecvMatrix->GetRawData(&dataLength_new, (const float**)(&pData_new)); for(int t=0;t<dataLength_new;t++) pData_new[t]=pDataRecv[t]; } switch (pGrModel->GetModelType()) { case mtBNet: { loglikOld = loglik; loglik = 0.0f; for(domainNodes = 0; domainNodes < numberOfParameters; domainNodes++) { parameter = pGrModel->GetFactor(domainNodes); loglik += parameter->ProcessingStatisticalData(m_numberOfAllEvidences); } break; } case mtMRF2: case mtMNet: { loglikOld = loglik; loglik = _LearnPotentials(); break; } default: { PNL_THROW(CBadConst, "model type") break; } } stopExpression = float(fabs(2 * (loglikOld - loglik) / (loglikOld + loglik))); exit = ((stopExpression > epsilon) && (iteration <= GetMaxIterEM())) && !itsML; if(exit) { ClearStatisticData(); } delete pCurrentInfEng; pCurrentInfEng = NULL; }while(exit); if(iteration > GetMaxIterEM()) { PNL_THROW(CNotConverged, "maximum number of iterations") } SetNumProcEv( GetNumEv() ); }
int testShrinkObservedNodes() { int i/*,j*/; int ret = TRS_OK; /*prepare to read the values from console*/ EDistributionType dt; int disType = -1; EFactorType pt; int paramType = -1; /*read int disType corresponding DistributionType*/ while((disType<0)||(disType>0))/*now we have only Tabulars&Gaussian*/ { trsiRead( &disType, "0", "DistributionType"); } /*read int paramType corresponding FactorType*/ while((paramType<0)||(paramType>2)) { trsiRead( ¶mType, "0", "FactorType"); } dt = EDistributionType(disType); pt = EFactorType(paramType); int numberOfNodes = 0; /*read number of nodes in Factor domain*/ while(numberOfNodes<=0) { trsiRead( &numberOfNodes, "1", "Number of Nodes in domain"); } int numNodeTypes = 0; /*read number of node types in model*/ while(numNodeTypes<=0) { trsiRead( &numNodeTypes, "1", "Number of node types in Domain"); } //int seed1 = pnlTestRandSeed()/*%100000*/; /*create string to display the value*/ /* char *value = new char[20]; value = _itoa(seed1, value, 10); trsiRead(&seed1, value, "Seed for srand to define NodeTypes etc."); delete []value; trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "seed for rand = %d\n", seed1); int *domain = (int *)trsGuardcAlloc(numberOfNodes, sizeof(int)); CNodeType * allNodeTypes = (CNodeType*)trsGuardcAlloc(numNodeTypes, sizeof(CNodeType)); //To generate the NodeTypes we use rand()% and creates only Tabular now for(i=0; i<numNodeTypes; i++) { allNodeTypes[i] = CNodeType(1, 1+rand()%(numNodeTypes+3)); } */ /*load data for parameter::ShrinkObservedNodes from console*/ intVector domain; domain.assign( numberOfNodes, 0 ); nodeTypeVector allNodeTypes; allNodeTypes.assign( numNodeTypes, CNodeType() ); /*read node types*/ for(i=0; i < numNodeTypes; i++) { int IsDiscrete = -1; int NodeSize = -1; while((IsDiscrete<0)||(IsDiscrete>1)) /*now we have tabular & Gaussian nodes!! */ trsiRead(&IsDiscrete, "1", "Is the node discrete?"); while(NodeSize<0) trsiRead(&NodeSize, "2", "NodeSize of node"); allNodeTypes[i] = CNodeType( IsDiscrete != 0, NodeSize ); } const CNodeType **nodeTypesOfDomain = (const CNodeType**) trsGuardcAlloc(numberOfNodes, sizeof(CNodeType*)); int numData = 1; int *Ranges = (int*)trsGuardcAlloc(numberOfNodes, sizeof(int)); /*associate nodes to node types*/ for(i=0; i<numberOfNodes; i++) { domain[i] = i; int nodeAssociationToNodeType = -1; while((nodeAssociationToNodeType<0)||(nodeAssociationToNodeType>= numNodeTypes)) trsiRead(&nodeAssociationToNodeType, "0", "node i has type nodeAssociationToNodeType"); nodeTypesOfDomain[i] = &allNodeTypes[nodeAssociationToNodeType]; // nodeTypesOfDomain[i] = &allNodeTypes[rand()%numNodeTypes]; Ranges[i] = nodeTypesOfDomain[i]->GetNodeSize(); numData=numData*Ranges[i]; } CModelDomain* pMD = CModelDomain::Create( allNodeTypes, domain ); /*create factor according all information*/ CFactor *pMyParam = NULL; float *data = (float *)trsGuardcAlloc(numData, sizeof(float)); char *stringVal;/* = (char*)trsGuardcAlloc(50, sizeof(char));*/ double val=0; /*read the values from console*/ if(pt == ftPotential) { pMyParam = CTabularPotential::Create( &domain.front(), numberOfNodes, pMD ); /*here we can create data by multiply on 0.1 - numbers are nonnormalized*/ for(i=0; i<numData; i++) { val = 0.1*i; stringVal = trsDouble(val); trsdRead(&val, stringVal, "value of i's data position"); data[i] = (float)val; //data[i] = (float)rand()/1000; } } else { /*we can only read data from console - it must be normalized!! (according their dimensions) - or we can normalize it by function!*/ if(pt == ftCPD) pMyParam = CTabularCPD::Create( &domain.front(), numberOfNodes, pMD ); for(i=0; i<numData; i++) { val = -1; while((val<0)||(val>1)) { trsdRead(&val, "-1", "value of (2*i)'s data position"); } data[i] = (float)val; } } //trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "data for Factor = %d\n", data[i]); pMyParam->AllocMatrix(data,matTable); int nObsNodes = 0; /*rand()%numberOfNodes;*/ while((nObsNodes<=0)||(nObsNodes>numberOfNodes)) { trsiRead(&nObsNodes, "1", "Number of Observed Nodes"); } intVector myHelpForEvidence = intVector(domain.begin(), domain.end() ); int *ObsNodes = (int *)trsGuardcAlloc(nObsNodes, sizeof(int)); valueVector TabularValues; TabularValues.assign( nObsNodes, (Value)0 ); char *strVal; for(i=0; i<nObsNodes; i++) { //fixme - we need to have noncopy only different ObsNodes /* j = rand()%(numberOfNodes-i);*/ int numberOfObsNode = -1; strVal = trsInt(i); intVector::iterator j = std::find( myHelpForEvidence.begin(), myHelpForEvidence.end(), numberOfObsNode ); while((numberOfObsNode<0)||(numberOfObsNode>numberOfNodes)|| (j==myHelpForEvidence.end())) { trsiRead(&numberOfObsNode, strVal,"Number of i's observed node"); j = std::find(myHelpForEvidence.begin(), myHelpForEvidence.end(), numberOfObsNode); } //ObsNodes[i] = myHelpForEvidence[j]; myHelpForEvidence.erase( j ); ObsNodes[i] = numberOfObsNode; int valueOfNode = -1; int maxValue = (*nodeTypesOfDomain[ObsNodes[i]]).GetNodeSize(); while((valueOfNode<0)||(valueOfNode>=maxValue)) { trsiRead(&valueOfNode,"0","this is i's observed node value"); } TabularValues[i].SetInt(valueOfNode); /*rand()%((*nodeTypesOfDomain[ObsNodes[i]]).pgmGetNodeSize());*/ } CEvidence* pEvidence = CEvidence::Create( pMD, nObsNodes, ObsNodes, TabularValues ); myHelpForEvidence.clear(); CNodeType *ObservedNodeType = (CNodeType*)trsGuardcAlloc(1, sizeof(CNodeType)); *ObservedNodeType = CNodeType(1,1); CPotential *myTakedInFactor = static_cast<CPotential*>(pMyParam)->ShrinkObservedNodes(pEvidence); const int *myfactorDomain; int factorDomSize ; myTakedInFactor->GetDomain(&factorDomSize, &myfactorDomain); #if 0 CNumericDenseMatrix<float> *mySmallMatrix = static_cast< CNumericDenseMatrix<float>*>(myTakedInFactor->GetMatrix(matTable)); int n; const float* mySmallData; mySmallMatrix->GetRawData(&n, &mySmallData); int nDims; // = mySmallMatrix->GetNumberDims(); const int * mySmallRanges; mySmallMatrix->GetRanges(&nDims, &mySmallRanges); if(nDims!=numberOfNodes) { ret = TRS_FAIL; trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "nDims = %d\n", nDims); } else { int numSmallData = 1; for(i=0; i<nDims; i++) { numSmallData = numSmallData*mySmallRanges[i]; trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "Range[%d] = %d\n", i, mySmallRanges[i]); } for(i=0; i<numSmallData; i++) { trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "mySmallData[%d] = %f ", i, mySmallData[i]); } } #endif //getchar(); delete(myTakedInFactor); delete (pMyParam); delete pMD; //test gaussian parameter nodeTypeVector nTypes; nTypes.assign( 2, CNodeType() ); nTypes[0] = CNodeType( 0, 2 ); nTypes[1] = CNodeType( 0,1 ); intVector domn = intVector(3,0); domn[1] = 1; domn[2] = 1; CModelDomain* pMD1 = CModelDomain::Create( nTypes, domn ); domn[2] = 2; CPotential *BigFactor = CGaussianPotential::CreateUnitFunctionDistribution( &domn.front(), domn.size(), pMD1,0 ); float mean[] = { 1.0f, 3.2f}; CPotential *SmallDelta = CGaussianPotential::CreateDeltaFunction( &domn.front(), 1, pMD1, mean, 1 ); domn.resize( 2 ); domn[0] = 1; domn[1] = 2; CPotential *SmallFunct = CGaussianPotential::Create( &domn.front(), domn.size(), pMD1); float datH[] = { 1.1f, 2.2f, 3.3f }; float datK[] = { 1.2f, 2.3f, 2.3f, 3.4f, 5.6f, 6.7f, 3.4f, 6.7f, 9.0f }; SmallFunct->AllocMatrix( datH, matH ); SmallFunct->AllocMatrix( datK, matK ); static_cast<CGaussianPotential*>(SmallFunct)->SetCoefficient( 0.2f, 1 ); CPotential* multFact = BigFactor->Multiply( SmallDelta ); CPotential* nextMultFact = multFact->Multiply( SmallFunct ); domn[0] = 0; domn[1] = 1; CPotential *marginalized = static_cast<CPotential*>(nextMultFact->Marginalize( &domn.front(), domn.size() )); int isSpecific = marginalized->IsDistributionSpecific(); if( isSpecific ) { trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "\nGaussian Distribution is specific"); } delete BigFactor; delete SmallFunct; delete SmallDelta; delete pMD1; int ranges_memory_flag = trsGuardCheck(Ranges); int data_memory_flag = trsGuardCheck(data); int nodeTypesOfDomain_mem_b = trsGuardCheck(nodeTypesOfDomain); int ObsNodes_mem_b = trsGuardCheck(ObsNodes); int ObsNodeType_mem_b = trsGuardCheck(ObservedNodeType); if(((ranges_memory_flag)||(data_memory_flag)|| (nodeTypesOfDomain_mem_b)|| (ObsNodes_mem_b)||(ObsNodeType_mem_b))) { ret = TRS_FAIL; return trsResult( ret, ret == TRS_OK ? "No errors" : "Bad test on ShrinkObservedNodes Method - memory"); } else { trsGuardFree(ObservedNodeType); trsGuardFree(ObsNodes); trsGuardFree(nodeTypesOfDomain); trsGuardFree(data); trsGuardFree(Ranges); } return trsResult( ret, ret == TRS_OK ? "No errors" : "Bad test on ShrinkObservedNodes Method"); }
void CParEMLearningEngine::LearnContMPI() { CStaticGraphicalModel *pGrModel = this->GetStaticModel(); PNL_CHECK_IS_NULL_POINTER(pGrModel); PNL_CHECK_LEFT_BORDER(GetNumEv() - GetNumberProcEv() , 1); CInfEngine *pInfEng = NULL; pInfEng = CJtreeInfEngine::Create(pGrModel); float loglik = 0.0f; int domainNodes; CFactor *parameter = NULL; int numberOfParameters = pGrModel->GetNumberOfParameters(); int nFactors = pGrModel->GetNumberOfFactors(); const CEvidence *pEv; CFactor *pFactor; int iteration = 0; int ev; int i,numSelfEvidences,NumberOfProcesses, MyRank; int start_mpi, finish_mpi; MPI_Comm_size(MPI_COMM_WORLD, &NumberOfProcesses); MPI_Comm_rank(MPI_COMM_WORLD, &MyRank); if (IsAllObserved()) { int i; float **evid = NULL; EDistributionType dt; CFactor *factor = NULL; for (i = 0; i < nFactors; i++) { factor = pGrModel->GetFactor(i); factor->UpdateStatisticsML(&m_Vector_pEvidences[GetNumberProcEv()], GetNumEv() - GetNumberProcEv()); } m_critValue.push_back(UpdateModel()); } else { bool bContinue; const CPotential * pot; do { ClearStatisticData(); iteration++; numSelfEvidences = (GetNumEv() - GetNumberProcEv()) / NumberOfProcesses; start_mpi = GetNumberProcEv() + numSelfEvidences * MyRank; if (MyRank < NumberOfProcesses - 1) finish_mpi = start_mpi + numSelfEvidences; else finish_mpi = GetNumEv(); for(int ev = start_mpi; ev < finish_mpi; ev++) { bool bInfIsNeed = !GetObsFlags(ev)->empty(); pEv = m_Vector_pEvidences[ev]; if( bInfIsNeed ) { pInfEng->EnterEvidence(pEv, 0, 0); } int i; for( i = 0; i < nFactors; i++ ) { pFactor = pGrModel->GetFactor(i); int nnodes; const int * domain; pFactor->GetDomain( &nnodes, &domain ); if( bInfIsNeed && !IsDomainObserved(nnodes, domain, ev ) ) { pInfEng->MarginalNodes( domain, nnodes, 1 ); pot = pInfEng->GetQueryJPD(); pFactor->UpdateStatisticsEM( /*pInfEng->GetQueryJPD */ pot, pEv ); } else { pFactor->UpdateStatisticsML( &pEv, 1 ); } } } for(domainNodes = 0; domainNodes < numberOfParameters; domainNodes++ ) { parameter = pGrModel->GetFactor(domainNodes); C2DNumericDenseMatrix<float> *matMeanForSending; C2DNumericDenseMatrix<float> *matCovForSending; int dataLengthM,dataLengthC; const float *pMeanDataForSending; const float *pCovDataForSending; matMeanForSending = static_cast<C2DNumericDenseMatrix<float>*> ((parameter->GetDistribFun())->GetStatisticalMatrix(stMatMu)); matMeanForSending->GetRawData(&dataLengthM, &pMeanDataForSending); matCovForSending = static_cast<C2DNumericDenseMatrix<float>*> ((parameter->GetDistribFun())->GetStatisticalMatrix(stMatSigma)); matCovForSending->GetRawData(&dataLengthC, &pCovDataForSending); float *pMeanDataRecv = new float[dataLengthM]; float *pCovDataRecv = new float[dataLengthC]; MPI_Status status; MPI_Allreduce((void*)pMeanDataForSending, pMeanDataRecv, dataLengthM, MPI_FLOAT, MPI_SUM, MPI_COMM_WORLD); MPI_Allreduce((void*)pCovDataForSending, pCovDataRecv, dataLengthC, MPI_FLOAT, MPI_SUM, MPI_COMM_WORLD); memcpy((void*)pMeanDataForSending,pMeanDataRecv,dataLengthM*sizeof(float)); memcpy((void*)pCovDataForSending,pCovDataRecv,dataLengthC*sizeof(float)); } loglik = UpdateModel(); if( GetMaxIterEM() != 1) { bool flag = iteration == 1 ? true : (fabs(2*(m_critValue.back()-loglik)/(m_critValue.back() + loglik)) > GetPrecisionEM() ); bContinue = GetMaxIterEM() > iteration && flag; } else { bContinue = false; } m_critValue.push_back(loglik); }while(bContinue); } SetNumProcEv( GetNumEv() ); }
CBNet* CreateBNet() { // Creation Water-Sprinkler Bayesian network const int numOfNds = 4;//*<- // 1 STEP: // need to specify the graph structure of the model; // there are two way to do it CGraph *pGraph; // Graph creation using neighbors list int numOfNbrs[numOfNds] = { 2, 2, 2, 2 };//*<- int nbrs0[] = { 1, 2 };//*<- int nbrs1[] = { 0, 3 };//*<- int nbrs2[] = { 0, 3 };//*<- int nbrs3[] = { 1, 2 };//*<- // number of neighbors for every node int *nbrs[] = { nbrs0, nbrs1, nbrs2, nbrs3 };//*<- // neighbors can be of either one of the three following types: // a parent, a child (for directed arcs) or just a neighbor (for undirected graphs). // Accordingly, the types are ntParent, ntChild or ntNeighbor. ENeighborType nbrsTypes0[] = { ntChild, ntChild };//*<- ENeighborType nbrsTypes1[] = { ntParent, ntChild };//*<- ENeighborType nbrsTypes2[] = { ntParent, ntChild };//*<- ENeighborType nbrsTypes3[] = { ntParent, ntParent };//*<- ENeighborType *nbrsTypes[] = { nbrsTypes0, nbrsTypes1,nbrsTypes2, nbrsTypes3 };//*<- // this is creation of a directed graph for the BNet model using neighbors list pGraph = CGraph::Create( numOfNds, numOfNbrs, nbrs, nbrsTypes ); // 2 STEP: // Creation NodeType objects and specify node types for all nodes of the model. nodeTypeVector nodeTypes; // number of node types is 1, because all nodes are of the same type // all four are discrete and binary CNodeType nt(1,2);//*<- nodeTypes.push_back(nt); intVector nodeAssociation; // reflects association between node numbers and node types // nodeAssociation[k] is a number of node type object in the // node types array for the k-th node nodeAssociation.assign(numOfNds, 0); // 2 STEP: // Creation base for BNet using Graph, types of nodes and nodes association CBNet* pBNet = CBNet::Create( numOfNds, nodeTypes, nodeAssociation, pGraph ); // 3 STEP: // Allocation space for all factors of the model pBNet->AllocFactors(); // 4 STEP: // Creation factors and attach their to model //create raw data tables for CPDs float table0[] = { 0.5f, 0.5f };//*<- float table1[] = { 0.5f, 0.5f, 0.9f, 0.1f }; float table2[] = { 0.8f, 0.2f, 0.2f, 0.8f }; float table3[] = { 1.0f, 0.0f, 0.1f, 0.9f, 0.1f, 0.9f, 0.01f, 0.99f }; float* table[] = { table0, table1, table2, table3 };//*<- int i; for( i = 0; i < numOfNds; ++i ) { pBNet->AllocFactor(i); CFactor* pFactor = pBNet->GetFactor(i); pFactor->AllocMatrix( table[i], matTable ); } return pBNet; }
void CStaticStructLearnSEM::CreateNeighborCPDs(CBNet* pBNet, pCPDVector* vNeighborCPDs, EDGEOPVECTOR* vValidMoves, intVector* RevCorrespDel) { CGraph* pGraph = pBNet->GetGraph(); CDAG* pDAG = CDAG::Create(*pGraph); CModelDomain* pMD = pBNet->GetModelDomain(); intVector vDiscrete, vContinuous; intVector vAncestor, vDescent; intVector vMixture, vMix; const CNodeType* nt; CFactor* factor; int i, j, position; vAncestor.assign(m_vAncestor.begin(), m_vAncestor.end()); vDescent.assign(m_vDescent.begin(), m_vDescent.end()); pBNet->FindMixtureNodes(&vMix); for(i=0; i<vMix.size(); i++) { factor = pBNet->GetFactor(vMix[i]); j = static_cast<CMixtureGaussianCPD*>(factor) -> GetNumberOfMixtureNode(); vMixture.push_back(j); } for(i=0; i<m_nNodes; i++) { nt = pMD->GetVariableType(i); if( nt->IsDiscrete() ) { vDiscrete.push_back(i); } else vContinuous.push_back(i); } vValidMoves->clear(); vNeighborCPDs->clear(); RevCorrespDel->clear(); pDAG->GetAllValidMove(vValidMoves, &vMixture.front(), vMixture.size(), m_nMaxFanIn, &vDiscrete, &vContinuous, &vDescent, &vAncestor ); int nMoves = vValidMoves->size(); intVector domain; EDGEOP curMove; int start, end; for(i=0; i<nMoves; i++) { domain.clear(); curMove = (*vValidMoves)[i]; switch (curMove.DAGChangeType) { case DAG_DEL : start = curMove.originalEdge.startNode; end = curMove.originalEdge.endNode; factor = pBNet->GetFactor(end); factor->GetDomain(&domain); position = std::find(domain.begin(), domain.end(), start) - domain.begin(); domain.erase(domain.begin()+position); vNeighborCPDs->push_back(CreateRandomCPD(domain.size(), &domain.front(), pBNet)); break; case DAG_ADD : start = curMove.originalEdge.startNode; end = curMove.originalEdge.endNode; factor = pBNet->GetFactor(end); factor->GetDomain(&domain); domain.insert(domain.begin(), start); vNeighborCPDs->push_back(CreateRandomCPD(domain.size(), &domain.front(), pBNet)); break; case DAG_REV : end = curMove.originalEdge.startNode; start = curMove.originalEdge.endNode; factor = pBNet->GetFactor(end); factor->GetDomain(&domain); domain.insert(domain.begin(), start); vNeighborCPDs->push_back(CreateRandomCPD(domain.size(), &domain.front(), pBNet)); break; } } RevCorrespDel->assign(nMoves, -1); EDGEOP pre_move; for(i=0; i<nMoves; i++) { curMove = (*vValidMoves)[i]; if(curMove.DAGChangeType == DAG_REV) { start = curMove.originalEdge.startNode; end = curMove.originalEdge.endNode; for(j=0; j<nMoves; j++) { pre_move = (*vValidMoves)[j]; if( (start == pre_move.originalEdge.startNode) && (end == pre_move.originalEdge.endNode) && (pre_move.DAGChangeType == DAG_DEL) ) { (*RevCorrespDel)[i] = j; break; } } } } }
CFactor* CFactor::CopyWithNewDomain(const CFactor *factor, intVector &domain, CModelDomain *pMDNew, const intVector& /* obsIndices */) { int domSize = domain.size(); intVector domOld; factor->GetDomain( &domOld ); if( int(domOld.size()) != domSize ) { PNL_THROW( CBadArg, "number of nodes" ); } CModelDomain *pMDOld = factor->GetModelDomain(); //check is the types are the same const pConstNodeTypeVector* ntFactor = factor->GetArgType(); /* const CNodeType *nt; for( int i = 0; i < domSize; i++ ) { nt = (*ntFactor)[i]; if( nt->IsDiscrete() ) { if( nt->GetNodeSize() == 1 ) { if( *pMDOld->GetVariableType(domOld[i]) != *pMDNew->GetVariableType(domain[i])) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } else { if( *nt != *pMDNew->GetVariableType(domain[i]) ) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } } else { if( nt->GetNodeSize() == 0 ) { if( *pMDOld->GetVariableType(domOld[i]) != *pMDNew->GetVariableType(domain[i])) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } else { if( *nt != *pMDNew->GetVariableType(domain[i]) ) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } } } */ const CNodeType *nt; int i; intVector obsPositions; factor->GetObsPositions(&obsPositions); if( obsPositions.size() ) { intVector::iterator iterEnd = obsPositions.end(); for( i = 0; i < domSize; i++) { if( std::find( obsPositions.begin(),iterEnd, i) != iterEnd ) { if( *pMDOld->GetVariableType(domOld[i]) != *pMDNew->GetVariableType(domain[i])) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } } } else { for( i = 0; i < domSize; i++ ) { nt = (*ntFactor)[i]; if( *nt != *pMDNew->GetVariableType(domain[i]) ) { PNL_THROW(CInconsistentType, "types of variables should correspond"); } } } CFactor *pNewFactor; switch ( factor->GetFactorType() ) { case ftPotential: { switch ( factor->GetDistributionType() ) { case dtTabular: { pNewFactor = CTabularPotential:: Copy(static_cast<const CTabularPotential*>(factor) ); break; } case dtGaussian: { pNewFactor = CGaussianPotential:: Copy(static_cast<const CGaussianPotential*>(factor)); break; } case dtScalar: { pNewFactor = CScalarPotential:: Copy( static_cast<const CScalarPotential*>(factor) ); break; } default: { PNL_THROW(CNotImplemented, "distribution type" ); } } break; } case ftCPD: { switch ( factor->GetDistributionType() ) { case dtTabular: { pNewFactor = CTabularCPD:: Copy(static_cast<const CTabularCPD*>(factor)); break; } case dtGaussian: { pNewFactor = CGaussianCPD:: Copy(static_cast<const CGaussianCPD*>(factor)); break; } case dtCondGaussian: { pNewFactor = CGaussianCPD:: Copy(static_cast<const CGaussianCPD*>(factor)); break; } case dtSoftMax: { pNewFactor = CSoftMaxCPD:: Copy(static_cast<const CSoftMaxCPD*>(factor)); break; } case dtCondSoftMax: { pNewFactor = CSoftMaxCPD:: Copy(static_cast<const CSoftMaxCPD*>(factor)); break; } case dtMixGaussian: { pNewFactor = CMixtureGaussianCPD::Copy( static_cast<const CMixtureGaussianCPD*>(factor)); break; } default: { PNL_THROW(CNotImplemented, "distribution type" ); } } break; } default: { PNL_THROW(CNotImplemented, "factor type" ); } } PNL_CHECK_IF_MEMORY_ALLOCATED(pNewFactor); /* if( pMDNew == factor->GetModelDomain()) { return pNewFactor; } else*/ { pNewFactor->m_Domain = intVector(domain); pNewFactor->SetModelDomain(pMDNew, 0); return pNewFactor; } }
CExInfEngine< INF_ENGINE, MODEL, FLAV, FALLBACK_ENGINE1, FALLBACK_ENGINE2 >::CExInfEngine( CStaticGraphicalModel const *gm ) : CInfEngine( itEx, gm ), evidence_mine( false ), maximize( 0 ), MPE_ev( 0 ), query_JPD( 0 ), graphical_model( gm ) { int i, j, k; intVector dom; intVector conv; CFactor *fac; PNL_MAKE_LOCAL( CGraph *, gr, gm, GetGraph() ); PNL_MAKE_LOCAL( int, sz, gr, GetNumberOfNodes() ); gr->GetConnectivityComponents( &decomposition ); for ( i = decomposition.size(); i--; ) { std::sort( decomposition[i].begin(), decomposition[i].end() ); } if ( PNL_IS_EXINFENGINEFLAVOUR_UNSORTED( FLAV ) ) { gr->GetTopologicalOrder( &conv ); } orig2comp.resize( sz ); orig2idx.resize( sz ); for ( k = 2; k--; ) { for ( i = decomposition.size(); i--; ) { for ( j = decomposition[i].size(); j--; ) { orig2comp[decomposition[i][j]] = i; orig2idx[decomposition[i][j]] = j; } } if ( PNL_IS_EXINFENGINEFLAVOUR_UNSORTED( FLAV ) && k ) { for ( i = sz; i--; ) { decomposition[orig2comp[conv[i]]][orig2idx[conv[i]]] = i; } } else { break; } } graphs.resize( decomposition.size() ); models.resize( decomposition.size() ); engines.resize( decomposition.size() ); for ( i = decomposition.size(); i--; ) { graphs[i] = gr->ExtractSubgraph( decomposition[i] ); #if 0 std::cout << "graph " << i << std::endl; graphs[i]->Dump(); #endif } node_types.resize( decomposition.size() ); node_assoc.resize( decomposition.size() ); for ( i = 0, k = 0; i < decomposition.size(); ++i ) { node_types[i].resize( decomposition[i].size() ); node_assoc[i].resize( decomposition[i].size() ); for ( j = 0; j < decomposition[i].size(); ++j ) { node_types[i][j] = *gm->GetNodeType( decomposition[i][j] ); node_assoc[i][j] = j; } } for ( i = decomposition.size(); i--; ) { models[i] = MODEL::Create( decomposition[i].size(), node_types[i], node_assoc[i], graphs[i] ); } for ( i = 0; i < gm->GetNumberOfFactors(); ++i ) { fac = gm->GetFactor( i ); fac->GetDomain( &dom ); #if 0 std::cout << "Ex received orig factor" << std::endl; fac->GetDistribFun()->Dump(); #endif k = orig2comp[dom[0]]; for ( j = dom.size(); j--; ) { dom[j] = orig2idx[dom[j]]; } fac = CFactor::CopyWithNewDomain( fac, dom, models[k]->GetModelDomain() ); #if 0 std::cout << "Ex mangled it to" << std::endl; fac->GetDistribFun()->Dump(); #endif models[k]->AttachFactor( fac ); } for ( i = decomposition.size(); i--; ) { switch ( decomposition[i].size() ) { case 1: engines[i] = FALLBACK_ENGINE1::Create( models[i] ); continue; case 2: engines[i] = FALLBACK_ENGINE2::Create( models[i] ); continue; default: engines[i] = INF_ENGINE::Create( models[i] ); } } }
void CEMLearningEngine::LearnExtraCPDs(int nMaxFamily, pCPDVector* additionalCPDs, floatVector* additionalLLs) { CStaticGraphicalModel *pGrModel = this->GetStaticModel(); PNL_CHECK_IS_NULL_POINTER(pGrModel); PNL_CHECK_LEFT_BORDER(GetNumEv(), 1); int numberOfFactors = pGrModel->GetNumberOfFactors(); int numberOfAddFactors = additionalCPDs->size(); additionalLLs->resize(numberOfAddFactors); additionalLLs->clear(); m_vFamilyLogLik.resize(numberOfFactors); float loglik = 0.0f, ll; int i, ev; int iteration = 0; const CEvidence* pEv; CFactor *factor = NULL; int nnodes; const int * domain; bool bInfIsNeed; CInfEngine *pInfEng = m_pInfEngine; if (IsAllObserved()) { for (i = 0; i < numberOfFactors; i++) { factor = pGrModel->GetFactor(i); factor->UpdateStatisticsML(&m_Vector_pEvidences[GetNumberProcEv()], GetNumEv() - GetNumberProcEv()); } for( ev = 0; ev < GetNumEv() ; ev++) { pEv = m_Vector_pEvidences[ev]; for( i = 0; i < numberOfAddFactors; i++ ) { factor = static_cast<CFactor*>((*additionalCPDs)[i]); factor->UpdateStatisticsML( &pEv, 1 ); } } switch (pGrModel->GetModelType()) { case mtBNet: { for( i = 0; i<numberOfFactors; i++ ) { factor = pGrModel->GetFactor(i); ll = factor->ProcessingStatisticalData( GetNumEv()); m_vFamilyLogLik[i] = ll; loglik += ll; } for( i = 0; i < numberOfAddFactors; i++ ) { factor = static_cast<CFactor*>((*additionalCPDs)[i]); ll = factor->ProcessingStatisticalData( GetNumEv()); (*additionalLLs)[i] = ll; } break; } case mtMRF2: case mtMNet: { break; } default: { PNL_THROW(CBadConst, "model type" ) break; } } m_critValue.push_back(loglik); } else {
int CBICLearningEngine::DimOfModel(const CStaticGraphicalModel *pModel) { /* compute dimension of the model in (d) it using in BIC criterion: BIC = LogLic - 0.5*d*log(N) */ int nParam = pModel->GetNumberOfFactors(); CFactor *param = NULL; int dimOfModel = 0; int dim = 1; CMatrix<float> *matrix;; for (int i = 0; i < nParam; i++) { dim = 1; param = pModel->GetFactor(i); switch (param->GetFactorType()) { case ftCPD: { switch (param->GetDistributionType()) { case dtTabular: { matrix = param->GetMatrix(matTable); int size; const int *ranges; static_cast<CNumericDenseMatrix<float>*>(matrix)-> GetRanges(&size, &ranges); for(int j=0; j < size - 1; j++) { dim *= ranges[j]; } dim *= ranges[size-1]-1; break; }//case dtTabular case dtGaussian: { PNL_THROW(CNotImplemented,"Gaussian") break; }//case dtGaussian case dtCondGaussian: { PNL_THROW(CNotImplemented,"CondGaussian") break; }//case dtCondGaussian default: { PNL_THROW(CBadConst,"distribution type") break; } }//swith(param->GetFactorType) break; }//end case ftCPD case ftPotential: { PNL_THROW(CNotImplemented,"Factor") break; } default: { PNL_THROW(CBadConst,"FactorType") break; } }//end switch(param->GetFactor) dimOfModel += dim; }//end for(i) return dimOfModel; }
void CEMLearningEngine::Learn() { CStaticGraphicalModel *pGrModel = this->GetStaticModel(); PNL_CHECK_IS_NULL_POINTER(pGrModel); PNL_CHECK_LEFT_BORDER(GetNumEv() - GetNumberProcEv() , 1); CInfEngine *pInfEng = NULL; if (m_pInfEngine) { pInfEng = m_pInfEngine; } else { if (!m_bAllObserved) { pInfEng = CJtreeInfEngine::Create(pGrModel); m_pInfEngine = pInfEng; } } float loglik = 0.0f; int nFactors = pGrModel->GetNumberOfFactors(); const CEvidence *pEv; CFactor *pFactor; int iteration = 0; int ev; bool IsCastNeed = false; int i; for( i = 0; i < nFactors; i++ ) { pFactor = pGrModel->GetFactor(i); EDistributionType dt = pFactor->GetDistributionType(); if ( dt == dtSoftMax ) IsCastNeed = true; } float ** full_evid = NULL; if (IsCastNeed) { BuildFullEvidenceMatrix(&full_evid); } if (IsAllObserved()) { int i; float **evid = NULL; EDistributionType dt; CFactor *factor = NULL; for (i = 0; i < nFactors; i++) { factor = pGrModel->GetFactor(i); dt = factor->GetDistributionType(); if (dt != dtSoftMax) { factor->UpdateStatisticsML(&m_Vector_pEvidences[GetNumberProcEv()], GetNumEv() - GetNumberProcEv()); } else { intVector family; family.resize(0); pGrModel->GetGraph()->GetParents(i, &family); family.push_back(i); CSoftMaxCPD* SoftMaxFactor = static_cast<CSoftMaxCPD*>(factor); SoftMaxFactor->BuildCurrentEvidenceMatrix(&full_evid, &evid,family,m_Vector_pEvidences.size()); SoftMaxFactor->InitLearnData(); SoftMaxFactor->SetMaximizingMethod(m_MaximizingMethod); SoftMaxFactor->MaximumLikelihood(evid, m_Vector_pEvidences.size(), 0.00001f, 0.01f); SoftMaxFactor->CopyLearnDataToDistrib(); for (int k = 0; k < factor->GetDomainSize(); k++) { delete [] evid[k]; } delete [] evid; } } m_critValue.push_back(UpdateModel()); } else { bool bContinue; const CPotential * pot; /* bool IsCastNeed = false; int i; for( i = 0; i < nFactors; i++ ) { pFactor = pGrModel->GetFactor(i); EDistributionType dt = pFactor->GetDistributionType(); if ( dt == dtSoftMax ) IsCastNeed = true; } float ** full_evid; if (IsCastNeed) { BuildFullEvidenceMatrix(full_evid); }*/ do { ClearStatisticData(); iteration++; for( ev = GetNumberProcEv(); ev < GetNumEv() ; ev++ ) { bool bInfIsNeed = !GetObsFlags(ev)->empty(); pEv = m_Vector_pEvidences[ev]; if( bInfIsNeed ) { pInfEng->EnterEvidence(pEv, 0, 0); } int i; for( i = 0; i < nFactors; i++ ) { pFactor = pGrModel->GetFactor(i); int nnodes; const int * domain; pFactor->GetDomain( &nnodes, &domain ); if( bInfIsNeed && !IsDomainObserved(nnodes, domain, ev ) ) { pInfEng->MarginalNodes( domain, nnodes, 1 ); pot = pInfEng->GetQueryJPD(); if ( (!(m_Vector_pEvidences[ev])->IsNodeObserved(i)) && (IsCastNeed) ) { Cast(pot, i, ev, &full_evid); } EDistributionType dt; dt = pFactor->GetDistributionType(); if ( !(dt == dtSoftMax) ) pFactor->UpdateStatisticsEM( /*pInfEng->GetQueryJPD */ pot, pEv ); } else { if ((pFactor->GetDistributionType()) != dtSoftMax) pFactor->UpdateStatisticsML( &pEv, 1 ); } } } int i; /* printf ("\n My Full Evidence Matrix"); for (i=0; i<nFactors; i++) { for (j=0; j<GetNumEv(); j++) { printf ("%f ", full_evid[i][j]); } printf("\n"); } */ float **evid = NULL; EDistributionType dt; CFactor *factor = NULL; // int i; for (i = 0; i < nFactors; i++) { factor = pGrModel->GetFactor(i); dt = factor->GetDistributionType(); if (dt == dtSoftMax) { intVector family; family.resize(0); pGrModel->GetGraph()->GetParents(i, &family); family.push_back(i); CSoftMaxCPD* SoftMaxFactor = static_cast<CSoftMaxCPD*>(factor); SoftMaxFactor->BuildCurrentEvidenceMatrix(&full_evid, &evid,family,m_Vector_pEvidences.size()); SoftMaxFactor->InitLearnData(); SoftMaxFactor->SetMaximizingMethod(m_MaximizingMethod); // SoftMaxFactor->MaximumLikelihood(evid, m_numberOfLastEvidences, SoftMaxFactor->MaximumLikelihood(evid, m_Vector_pEvidences.size(), 0.00001f, 0.01f); SoftMaxFactor->CopyLearnDataToDistrib(); for (int k = 0; k < factor->GetDomainSize(); k++) { delete [] evid[k]; } delete [] evid; } } loglik = UpdateModel(); if( GetMaxIterEM() != 1) { bool flag = iteration == 1 ? true : (fabs(2*(m_critValue.back()-loglik)/(m_critValue.back() + loglik)) > GetPrecisionEM() ); bContinue = GetMaxIterEM() > iteration && flag; } else { bContinue = false; } m_critValue.push_back(loglik); }while(bContinue); } SetNumProcEv( GetNumEv() ); if (IsCastNeed) { int NumOfNodes = pGrModel->GetGraph()->GetNumberOfNodes(); for (i=0; i<NumOfNodes; i++) { delete [] full_evid[i]; } delete [] full_evid; } }
int testSetStatistics() { int ret = TRS_OK; float eps = 0.1f; int seed = pnlTestRandSeed(); pnlSeed( seed ); CBNet *pBNet = pnlExCreateCondGaussArBNet(); CModelDomain *pMD = pBNet->GetModelDomain(); CGraph *pGraph = CGraph::Copy(pBNet->GetGraph()); CBNet *pBNet1 = CBNet::CreateWithRandomMatrices( pGraph, pMD ); pEvidencesVector evidences; int nEvidences = pnlRand( 3000, 4000); pBNet->GenerateSamples( &evidences, nEvidences ); int i; for( i = 0; i < nEvidences; i++) { //evidences[i]->MakeNodeHiddenBySerialNum(0); } CEMLearningEngine *pLearn = CEMLearningEngine::Create(pBNet1); pLearn->SetData( nEvidences, &evidences.front() ); pLearn->SetMaxIterEM(); pLearn->Learn(); for( i = 0; i < pBNet->GetNumberOfFactors(); i++ ) { if( ! pBNet->GetFactor(i)->IsFactorsDistribFunEqual(pBNet1->GetFactor(i), eps)) { ret = TRS_FAIL; pBNet->GetFactor(i)->GetDistribFun()->Dump(); pBNet1->GetFactor(i)->GetDistribFun()->Dump(); } } CDistribFun *pDistr; const CMatrix<float>* pMat; CFactor *pCPD; pDistr = pBNet1->GetFactor(0)->GetDistribFun(); pMat = pDistr->GetStatisticalMatrix(stMatTable); pCPD = pBNet->GetFactor(0); pCPD->SetStatistics(pMat, stMatTable); pCPD->ProcessingStatisticalData(nEvidences); if( ! pCPD->IsFactorsDistribFunEqual(pBNet1->GetFactor(0), 0.0001f) ) { ret = TRS_FAIL; } pDistr = pBNet1->GetFactor(1)->GetDistribFun(); int parentVal; pCPD = pBNet->GetFactor(1); parentVal = 0; pCPD->SetStatistics(pMat, stMatCoeff); pMat = pDistr->GetStatisticalMatrix(stMatMu, &parentVal); pCPD->SetStatistics(pMat, stMatMu, &parentVal); pMat = pDistr->GetStatisticalMatrix(stMatSigma, &parentVal); pCPD->SetStatistics(pMat, stMatSigma, &parentVal); parentVal = 1; pMat = pDistr->GetStatisticalMatrix(stMatMu, &parentVal); pCPD->SetStatistics(pMat, stMatMu, &parentVal); pMat = pDistr->GetStatisticalMatrix(stMatSigma, &parentVal); pCPD->SetStatistics(pMat, stMatSigma, &parentVal); pCPD->ProcessingStatisticalData(nEvidences); if( ! pCPD->IsFactorsDistribFunEqual(pBNet1->GetFactor(1), eps) ) { ret = TRS_FAIL; } for( i = 0; i < nEvidences; i++) { delete evidences[i]; } delete pLearn; delete pBNet1; delete pBNet; return trsResult( ret, ret == TRS_OK ? "No errors" : "Bad test on SetStatistics"); }
void cfactor_setCounts(CFactor &fac, vector<map<size_t, int> > & counts) { fac.counts() = counts; }
int main() { PNL_USING //we create very small model to start inference on it // the model is from Kevin Murphy's BNT\examples\static\belprop_polytree_gaussain /* Do the example from Satnam Alag's PhD thesis, UCB ME dept 1996 p46 Make the following polytree, where all arcs point down 0 1 \ / 2 / \ 3 4 */ int i; //create this model int nnodes = 5; int numnt = 2; CNodeType *nodeTypes = new CNodeType[numnt]; nodeTypes[0] = CNodeType(0,2); nodeTypes[1] = CNodeType(0,1); intVector nodeAssociation = intVector(nnodes,0); nodeAssociation[1] = 1; nodeAssociation[3] = 1; int nbs0[] = { 2 }; int nbs1[] = { 2 }; int nbs2[] = { 0, 1, 3, 4 }; int nbs3[] = { 2 }; int nbs4[] = { 2 }; int *nbrs[] = { nbs0, nbs1, nbs2, nbs3, nbs4 }; int numNeighb[] = {1, 1, 4, 1, 1}; ENeighborType ori0[] = { ntChild }; ENeighborType ori1[] = { ntChild }; ENeighborType ori2[] = { ntParent, ntParent, ntChild, ntChild }; ENeighborType ori3[] = { ntParent }; ENeighborType ori4[] = { ntParent }; ENeighborType *orient[] = { ori0, ori1, ori2, ori3, ori4 }; CGraph *pGraph; pGraph = CGraph::Create(nnodes, numNeighb, nbrs, orient); CBNet *pBNet; pBNet = CBNet::Create( nnodes, numnt, nodeTypes, &nodeAssociation.front(), pGraph ); //Allocation space for all factors of the model pBNet->AllocFactors(); for( i = 0; i < nnodes; i++ ) { //Allocation space for all matrices of CPD pBNet->AllocFactor(i); } //now we need to create data for CPDs - we'll create matrices CFactor *pCPD; floatVector smData = floatVector(2,0.0f); floatVector bigData = floatVector(4,1.0f); intVector ranges = intVector(2, 1); ranges[0] = 2; smData[0] = 1.0f; CNumericDenseMatrix<float> *mean0 = CNumericDenseMatrix<float>:: Create( 2, &ranges.front(), &smData.front()); bigData[0] = 4.0f; bigData[3] = 4.0f; ranges[1] = 2; CNumericDenseMatrix<float> *cov0 = CNumericDenseMatrix<float>:: Create( 2, &ranges.front(), &bigData.front()); pCPD = pBNet->GetFactor(0); pCPD->AttachMatrix(mean0, matMean); pCPD->AttachMatrix(cov0, matCovariance); ranges[0] = 1; ranges[1] = 1; float val = 1.0f; CNumericDenseMatrix<float> *mean1 = CNumericDenseMatrix<float>:: Create( 2, &ranges.front(), &val ); CNumericDenseMatrix<float> *cov1 = CNumericDenseMatrix<float>:: Create( 2, &ranges.front(), &val ); pCPD = pBNet->GetFactor(1); pCPD->AttachMatrix(mean1, matMean); pCPD->AttachMatrix(cov1, matCovariance); smData[0] = 0.0f; smData[1] = 0.0f; ranges[0] = 2; CNumericDenseMatrix<float> *mean2 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &smData.front()); smData[0] = 2.0f; smData[1] = 1.0f; CNumericDenseMatrix<float> *w21 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &smData.front()); bigData[0] = 2.0f; bigData[1] = 1.0f; bigData[2] = 1.0f; bigData[3] = 1.0f; ranges[1] = 2; CNumericDenseMatrix<float> *cov2 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &bigData.front()); bigData[0] = 1.0f; bigData[1] = 2.0f; bigData[2] = 1.0f; bigData[3] = 0.0f; CNumericDenseMatrix<float> *w20 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &bigData.front()); pCPD = pBNet->GetFactor(2); pCPD->AttachMatrix( mean2, matMean ); pCPD->AttachMatrix( cov2, matCovariance ); pCPD->AttachMatrix( w20, matWeights,0 ); pCPD->AttachMatrix( w21, matWeights,1 ); val = 0.0f; ranges[0] = 1; ranges[1] = 1; CNumericDenseMatrix<float> *mean3 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &val); val = 1.0f; CNumericDenseMatrix<float> *cov3 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &val); ranges[1] = 2; smData[0] = 1.0f; smData[1] = 1.0f; CNumericDenseMatrix<float> *w30 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &smData.front()); pCPD = pBNet->GetFactor(3); pCPD->AttachMatrix( mean3, matMean ); pCPD->AttachMatrix( cov3, matCovariance ); pCPD->AttachMatrix( w30, matWeights,0 ); ranges[0] = 2; ranges[1] = 1; smData[0] = 0.0f; smData[1] = 0.0f; CNumericDenseMatrix<float> *mean4 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &smData.front()); ranges[1] = 2; bigData[0] = 1.0f; bigData[1] = 0.0f; bigData[2] = 0.0f; bigData[3] = 1.0f; CNumericDenseMatrix<float> *cov4 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &bigData.front()); bigData[2] = 1.0f; CNumericDenseMatrix<float> *w40 = CNumericDenseMatrix<float>:: Create(2, &ranges.front(), &bigData.front()); pCPD = pBNet->GetFactor(4); pCPD->AttachMatrix( mean4, matMean ); pCPD->AttachMatrix( cov4, matCovariance ); pCPD->AttachMatrix( w40, matWeights,0 ); //Generate random evidences for the modes int nEv = 1000; pEvidencesVector evid; pBNet->GenerateSamples( &evid, nEv ); ///////////////////////////////////////////////////////////////////// //Create copy of initial model with random matrices CGraph *pGraphCopy = CGraph::Copy(pGraph); CBNet *pLearnBNet = CBNet::CreateWithRandomMatrices(pGraphCopy, pBNet->GetModelDomain() ); // Creating learning process CEMLearningEngine *pLearn = CEMLearningEngine::Create(pLearnBNet); pLearn->SetData(nEv, &evid.front()); pLearn->Learn(); CNumericDenseMatrix<float> *pMatrix; int length = 0; const float *output; /////////////////////////////////////////////////////////////////////// std::cout<<" results of learning (number of evidences = "<<nEv<<std::endl; for (i = 0; i < nnodes; i++ ) { int j; std::cout<<"\n matrix mean for node "<<i; std::cout<<"\n initial BNet \n"; pMatrix = static_cast<CNumericDenseMatrix<float>*> (pBNet->GetFactor(i)->GetMatrix(matMean)); pMatrix->GetRawData(&length, &output); for ( j = 0; j < length; j++ ) { std::cout<<" "<<output[j]; } std::cout<<"\n BNet with random matrices after learning \n "; pMatrix = static_cast<CNumericDenseMatrix<float>*> (pLearnBNet->GetFactor(i)->GetMatrix(matMean)); pMatrix->GetRawData(&length, &output); for ( j = 0; j < length; j++) { std::cout<<" "<<output[j]; } std::cout<<"\n \n matrix covariance for node "<<i<<'\n'; std::cout<<"\n initial BNet \n"; pMatrix = static_cast<CNumericDenseMatrix<float>*> (pBNet->GetFactor(i)->GetMatrix(matCovariance)); pMatrix->GetRawData(&length, &output); for (j = 0; j < length; j++ ) { std::cout<<" "<<output[j]; } std::cout<<"\n BNet with random matrices after learning \n "; pMatrix = static_cast<CNumericDenseMatrix<float>*> (pLearnBNet->GetFactor(i)->GetMatrix(matCovariance)); pMatrix->GetRawData(&length, &output); for ( j = 0; j < length; j++ ) { std::cout<<" "<<output[j]; } std::cout<<"\n ___________________________\n"; } for( i = 0; i < nEv; i++) { delete evid[i]; } delete pLearn; delete pLearnBNet; delete pBNet; return 1; }
void CSoftMaxCPD::CreateMeanAndCovMatrixForNode(int Node, const CEvidence* pEvidence, const CBNet *pBNet, floatVector &Mean, C2DNumericDenseMatrix<float>**CovContParents) const { int i, j, k; int *multiindex = new int [2]; intVector contParents; pBNet->GetContinuousParents(Node, &contParents); intVector lineSizes; lineSizes.assign(2, contParents.size()); floatVector zerodata; zerodata.assign(contParents.size()*contParents.size(), 0.0f); *CovContParents = C2DNumericDenseMatrix<float>::Create( &lineSizes.front(), &zerodata.front() ); for (i = 0; i < contParents.size(); i++ ) { for (j = 0; j < contParents.size(); j++ ) { multiindex[0] = i; multiindex[1] = j; (*CovContParents)->SetElementByIndexes(0.0f, multiindex); } } intVector pObsNodes; pConstValueVector pObsValues; pConstNodeTypeVector pNodeTypes; pEvidence->GetObsNodesWithValues(&pObsNodes, &pObsValues, &pNodeTypes); Mean.resize(0); for ( i = 0; i < contParents.size(); i++) { int CurNode = contParents[i]; CFactor *param; param = pBNet->GetFactor(CurNode); intVector parentOut; intVector DiscrParents; pBNet->GetDiscreteParents(CurNode, &DiscrParents); int *parentComb = new int [DiscrParents.size()]; for ( j = 0; j < DiscrParents.size(); j++) { for ( k = 0; k < pObsNodes.size(); k++) { if (DiscrParents[j] == pObsNodes[k]) { parentComb[j] = pObsValues[k]->GetInt(); break; } } } const float *data; int datasize; static_cast<CDenseMatrix<float>*>(param->GetMatrix(matMean, -1, parentComb))-> GetRawData(&datasize, &data); Mean.push_back(data[0]); static_cast<CDenseMatrix<float>*>(param->GetMatrix(matCovariance, -1, parentComb))-> GetRawData(&datasize, &data); multiindex[0] = i; multiindex[1] = i; (*CovContParents)->SetElementByIndexes(data[0], multiindex); delete [] parentComb; } delete [] multiindex; }