- Main Page
- Namespaces
- Classes
- Files
- Related Pages

# /Users/fpy/titan-1-5-MBARI/Mers/Estimation/Discrete/ProbabilityRules/RuleGenerator/ProbRuleGenerator.cpp

    00001 //==============================================================================
    00002 // Copyright (c) 2005           Model-based Embedded and Robotic Systems Group
    00003 // All Rights Reserved          Massachusetts Institute of Technology
    00004 //
    00005 // This software is provided as is. Model-based Embedded and Robotic Systems
    00006 // (MERS) group does not assume any responsibility.
    00007 //==============================================================================
    00008
    00009 #include "ProbRuleGenerator.h"
    00010
    00011 #ifdef _MSC_VER
    00012 #pragma warning( disable : 4786 )
    00013 #endif
    00014
    00015 #include <Mers/Estimation/Discrete/Dissent.h>
    00016 #include <Mers/Estimation/Discrete/ProbabilityRules/Rule.h>
    00017 #include <Mers/Estimation/Discrete/ProbabilityRules/IndexedRule.h>
    00018 #include <Mers/Estimation/Discrete/ProbabilityRules/ObsComboRule.h>
    00019 #include <Mers/Estimation/Discrete/ProbabilityRules/ObsProbRule.h>
    00020 #include <Mers/Estimation/Discrete/ProbabilityRules/RuleTriggering/RuleTrigger.h>
    00021 #include <Mers/Utils/Containers/IntegerArray.h>
    00022 #include <Mers/Models/Base/BaseModel.h>
    00023 #include <Mers/Models/Base/BaseModelVariable.h>
    00024 #include <Mers/Models/Base/BaseModelAssignment.h>
    00025 #include <Mers/Models/Base/BaseModelAssignmentArray.h>
    00026
    00027 using namespace Mers::Estimation::Discrete::ProbabilityRules::RuleGenerator;
    00028 using Mers::Estimation::Discrete::ProbabilityRules::RuleTriggering::RuleTrigger;
    00029 using Mers::Estimation::Discrete::ProbabilityRules::Rule;
    00030 using Mers::Estimation::Discrete::ProbabilityRules::IndexedRule;
    00031 using Mers::Estimation::Discrete::ProbabilityRules::ObsProbRule;
    00032 using Mers::Estimation::Discrete::ProbabilityRules::ObsComboRule;
    00033 using Mers::Models::Base::BaseModel;
    00034 using Mers::Models::Base::BaseModelVariable;
    00035 using Mers::Models::Base::BaseModelAssignment;
    00036 using Mers::Models::Base::BaseModelAssignmentArray;
    00037 using Mers::Estimation::Discrete::Dissent;
    00038 using Mers::Utils::Containers::IntegerArray;
    00039 using std::vector;
    00040 using std::ostream;
    00041 using std::endl;
    00042 using std::cout;
    00043 using std::cerr;
    00044
    00045
    00046         //-----------------------------------------------
    00047         //      CONSTRUCTOR
    00048         //-----------------------------------------------
    00049
    00050
    00051 ProbRuleGenerator::ProbRuleGenerator(const Mers::Models::Base::BaseModel * theBMp,
    00052                 const std::vector<const Mers::Estimation::Discrete::Dissent *> theDissentsVec,
    00053                 unsigned short db)
    00054 : model_p(theBMp), dissents_vec(theDissentsVec), debug(db)
    00055 {}
    00056         //-----------------------------------------------
    00057         //      DESTRUCTOR
    00058         //-----------------------------------------------
    00059
    00060
    00061 ProbRuleGenerator::~ProbRuleGenerator()
    00062 {
    00063 }
    00064
    00065
    00066
    00067         //-----------------------------------------------
    00068         //      PUBLIC METHODS
    00069         //-----------------------------------------------
    00070
    00071 const vector<const ObsProbRule *>
    00072 ProbRuleGenerator::getObservationRules(void) const
    00073 {
    00074         size_t i;
    00075         vector<const ObsProbRule *> obsProbabilityRules;
    00076         vector<IntegerArray *> obsComponentGroupingVectorByUID;
    00077         vector<IntegerArray *> dissentToGroupMap;
    00078         vector<const ObsProbRule *> dependencyGroupObsProbRules;
    00079
    00080         cout << "Generating observation probability rules..." << endl;
    00081
    00082         // Identify which observations are dependent on which components
    00083         getObservationAndComponentDependencies(obsComponentGroupingVectorByUID, dissentToGroupMap);
    00084
    00085         if(debug > 1)
    00086         {
    00087                 for(i = 0; i < obsComponentGroupingVectorByUID.size(); i++)
    00088                 {
    00089                         cout << "grp " << (unsigned int)i << ": " << *obsComponentGroupingVectorByUID[i] << endl;
    00090                         cout << "   created from dissent ids: " << *dissentToGroupMap[i] << endl;
    00091                 }
    00092         }
    00093
    00094
    00095         for(i = 0; i < obsComponentGroupingVectorByUID.size(); i++)
    00096         {
    00097                 if(debug > 0)
    00098                         cout << "--- Group # " << (unsigned int)i << " ---" << endl;
    00099                 // Determine the total number of combinations of observations assignments and mode
    00100                 // assignments there are for each grouping. Search through all the dissents to
    00101                 // eliminate inconsistent observation and mode assignment combinations. Determine
    00102                 // the number of consistent observations to each set of mode assignments and prune
    00103                 // the ones that have 1 or 0 consistent mode assignments (BFIG handles these automatically).
    00104                 dependencyGroupObsProbRules = determineNumConsistentObs(obsComponentGroupingVectorByUID[i], dissentToGroupMap[i]);
    00105
    00106
    00107                 while(dependencyGroupObsProbRules.size() > 0)
    00108                 {
    00109                         obsProbabilityRules.push_back(dependencyGroupObsProbRules.back());
    00110                         dependencyGroupObsProbRules.pop_back();
    00111                 }
    00112
    00113                 // Clean up
    00114                 delete obsComponentGroupingVectorByUID[i];
    00115                 delete dissentToGroupMap[i];
    00116         }
    00117
    00118         cout << "Success!" << endl;
    00119
    00120         return obsProbabilityRules;
    00121 }
    00122
    00123
    00124 void
    00125 ProbRuleGenerator::setDebug(const unsigned short db)
    00126 {
    00127         debug = db;
    00128         return;
    00129 }
    00130
    00131
    00132 ostream&
    00133 Mers::Estimation::Discrete::ProbabilityRules::RuleGenerator::operator<<(ostream& os, ProbRuleGenerator const & prg)
    00134 {
    00135         os << "This is the probability rule generator." << endl;
    00136
    00137         return os;
    00138 }
    00139         //-----------------------------------------------
    00140         //      PRIVATE METHODS
    00141         //-----------------------------------------------
    00142
    00143 bool
    00144 ProbRuleGenerator::getObservationAndComponentDependencies(
    00145                 vector<IntegerArray *> & obsCompDependencies_vec,
    00146                 vector<IntegerArray *> & dissentIDgroup ) const
    00147 {
    00148         size_t i, j;
    00149         unsigned int k, l;
    00150         bool foundMatch = false;
    00151         IntegerArray * dissentVariableUIDs;
    00152         IntegerArray * previousDependencyGroupIndices;
    00153         int baseIndex, copyIndex, element;
    00154
    00155
    00156         if(dissents_vec.size() == 0)
    00157         {
    00158                 cout << "<ProbRuleGenerator> WARNING: No dissents provided." << endl;
    00159                 return false;
    00160         }
    00161
    00162         if(obsCompDependencies_vec.size() != 0 || dissentIDgroup.size() != 0)
    00163         {
    00164                 cout << "<ProbRuleGenerator> ERROR: input reference parameters are non-zero vectors!" << endl;
    00165                 return false;
    00166         }
    00167
    00168         previousDependencyGroupIndices = new IntegerArray();
    00169         dissentVariableUIDs = new IntegerArray();
    00170
    00171         // Iterate through all dissents
    00172         for(i=0; i < dissents_vec.size(); i++)
    00173         {
    00174                 const unsigned int antLength = dissents_vec[i]->getAntecedentLength();
    00175                 if(antLength > 0)
    00176                 {
    00177                         // Get all the UIDs for this dissent
    00178                         for(k = 0; k < antLength; k++)
    00179                                 dissentVariableUIDs->pushBack(dissents_vec[i]->getAntecedentVariableUID(k));
    00180                         const BaseModelAssignmentArray * aConflict = dissents_vec[i]->getConflict();
    00181                         for(k = 0; k < aConflict->getLength(); k++)
    00182                                 dissentVariableUIDs->pushBack((*aConflict)[k]->getVariable()->getUID());
    00183
    00184                         if(debug > 2)
    00185                                 cout << "Dissent Var Ids: " << *dissentVariableUIDs << endl;
    00186
    00187                         // See if the var UIDs are already dependent on another variable
    00188                         for(j = obsCompDependencies_vec.size(); j > 0; j--) // Done backwards so the popback function
    00189                         {                                                   // will return the lowest number
    00190                                 foundMatch = false;
    00191                                 for(k = 0; k < obsCompDependencies_vec[j-1]->getLength() && !foundMatch; k++)
    00192                                 {
    00193                                         for(l = 0; l < dissentVariableUIDs->getLength() && !foundMatch; l++)
    00194                                         {
    00195                                                 if((*obsCompDependencies_vec[j-1])[k] == (*dissentVariableUIDs)[l])
    00196                                                 {
    00197                                                         previousDependencyGroupIndices->pushBack((unsigned int)j-1);
    00198                                                         foundMatch = true;
    00199                                                 }
    00200                                         }
    00201                                 }
    00202                         }
    00203                         // If there was a match with more than one group, the groups must be combined
    00204                         if(previousDependencyGroupIndices->getLength() > 1)
    00205                         {
    00206                                 baseIndex = previousDependencyGroupIndices->popBack();
    00207                                 l = 0;
    00208                                 while(previousDependencyGroupIndices->getLength() > 0)
    00209                                 {
    00210                                         copyIndex = previousDependencyGroupIndices->popBack() - l; // Need to shift index each time one is deleted
    00211                                         *obsCompDependencies_vec[baseIndex] += *obsCompDependencies_vec[copyIndex];
    00212                                         *dissentIDgroup[baseIndex] += *dissentIDgroup[copyIndex];
    00213                                         delete obsCompDependencies_vec[copyIndex];
    00214                                         delete dissentIDgroup[copyIndex];
    00215                                         for(k = copyIndex; k < obsCompDependencies_vec.size()-1; k++)
    00216                                         {
    00217                                                 obsCompDependencies_vec[k] = obsCompDependencies_vec[k+1];
    00218                                                 dissentIDgroup[k] = dissentIDgroup[k+1];
    00219                                         }
    00220                                         obsCompDependencies_vec.pop_back();
    00221                                         dissentIDgroup.pop_back();
    00222                                         l++;
    00223                                 }
    00224                                 previousDependencyGroupIndices->pushBack(baseIndex);
    00225                         }
    00226
    00227                         if(previousDependencyGroupIndices->getLength() == 1) // Add the dependencies to the group
    00228                         {
    00229                                 baseIndex = previousDependencyGroupIndices->popBack();
    00230                                 while(dissentVariableUIDs->getLength() > 0)
    00231                                 {
    00232                                         element = dissentVariableUIDs->popBack();
    00233                                         foundMatch = false;
    00234                                         for(l = 0; l < obsCompDependencies_vec[baseIndex]->getLength() && !foundMatch; l++)
    00235                                         {
    00236                                                 if((*obsCompDependencies_vec[baseIndex])[l] == element)
    00237                                                         foundMatch = true;
    00238                                         }
    00239                                         if(!foundMatch)
    00240                                                 obsCompDependencies_vec[baseIndex]->pushBack(element);
    00241                                 }
    00242                                 dissentIDgroup[baseIndex]->pushBack((unsigned int)i);           // Add this dissent id to the appropriate group
    00243                         }
    00244                         else if(previousDependencyGroupIndices->getLength() == 0)  // No depencies listed yet, start a new group
    00245                         {
    00246                                 obsCompDependencies_vec.resize(obsCompDependencies_vec.size()+1);
    00247                                 obsCompDependencies_vec[obsCompDependencies_vec.size()-1] = new IntegerArray();
    00248                                 while(dissentVariableUIDs->getLength() > 0)
    00249                                         obsCompDependencies_vec[obsCompDependencies_vec.size()-1]->pushBack(dissentVariableUIDs->popBack());
    00250                                 dissentIDgroup.resize(dissentIDgroup.size()+1);
    00251                                 dissentIDgroup[dissentIDgroup.size()-1] = new IntegerArray();
    00252                                 dissentIDgroup[dissentIDgroup.size()-1]->pushBack((unsigned int)i);   // Add this dissent id to the appropriate group
    00253
    00254                         }
    00255                         else
    00256                                 cerr << "<ProbRuleGenerator> ERROR: previousDependencyGroupIndices is not empty!!" << endl;
    00257
    00258
    00259                         if(dissentVariableUIDs->getLength() != 0)
    00260                                 cerr << "<ProbRuleGenerator> ERROR: dissentVariableUIDs is not empty!!" << endl;
    00261                 }
    00262                 // else: this dissent is not relevent to the observation probability rules
    00263         }
    00264
    00265         delete previousDependencyGroupIndices;
    00266         delete dissentVariableUIDs;
    00267
    00268         if(dissentIDgroup.size() != obsCompDependencies_vec.size())
    00269         {
    00270                 cerr << "<ProbRuleGenerator> ERROR: Number of dependency groups are different!" << endl;
    00271                 return false;
    00272         }
    00273
    00274         return true;
    00275 }
    00276
    00277 vector<const ObsProbRule *>
    00278 ProbRuleGenerator::determineNumConsistentObs(
    00279                 const Mers::Utils::Containers::IntegerArray * varIDs,
    00280                 const Mers::Utils::Containers::IntegerArray * relevantDissentIDs) const
    00281 {
    00282
    00283         unsigned int i, j, k, varID, domainSize;
    00284         bool allCombosExpanded = false;
    00285         vector<Rule *> allRelevantConflictRules;
    00286         vector<Rule *> allModeComboRules;
    00287         vector<Rule *> allObsComboRules;
    00288         vector<Rule *> enabledObsRules;
    00289         vector<Rule *> enabledConflictRules;
    00290         vector<Rule *> relevantObsRules;
    00291         vector<const ObsProbRule *> groupsObservationProbs;
    00292         IntegerArray * modeDomainSizes = new IntegerArray();
    00293         IntegerArray * modeVarIDs = new IntegerArray();
    00294         IntegerArray * currentValIDs = new IntegerArray();
    00295         IntegerArray * obsDomainSizes = new IntegerArray();
    00296         IntegerArray * obsVarIDs = new IntegerArray();
    00297         IntegerArray * currentObsValIDs = new IntegerArray();
    00298         BaseModelAssignmentArray * ruleAssignments;
    00299         RuleTrigger * obsTrigger;
    00300         RuleTrigger * conflictTrigger;
    00301         unsigned int numCombosObsAssigns = 1;
    00302
    00303         // Determine the total number of combinations of observations assignments and mode
    00304         // assignments there are for each grouping
    00305         for(j = 0; j < varIDs->getLength(); j++)
    00306         {
    00307                 varID = (*varIDs)[j];
    00308                 domainSize = model_p->getVariable(varID)->getDomain()->getLength();
    00309                 if(model_p->getVariable(varID)->getVariableType() == BaseModelVariable::OBSERVABLE)
    00310                 {
    00311                         numCombosObsAssigns *= domainSize;
    00312                         obsVarIDs->pushBack(varID);
    00313                         obsDomainSizes->pushBack(domainSize);
    00314                         currentObsValIDs->pushBack(0);
    00315                 }
    00316                 else if(model_p->getVariable(varID)->getVariableType() == BaseModelVariable::STATE)
    00317                 {
    00318                         modeVarIDs->pushBack(varID);
    00319                         modeDomainSizes->pushBack(domainSize);
    00320                         currentValIDs->pushBack(0);
    00321                 }
    00322                 else
    00323                         cerr << "<ProbRuleGenerator> ERROR: Dissents should only have obs and mode vars!!" << endl;
    00324         }
    00325
    00326         // Generate mode combination rules
    00327         while(!allCombosExpanded)
    00328         {
    00329                 ruleAssignments = new BaseModelAssignmentArray(true);
    00330                 for(j = 0; j < modeVarIDs->getLength(); j++)
    00331                 {
    00332                         ruleAssignments->pushBack(new BaseModelAssignment(model_p->getVariable((*modeVarIDs)[j]),
    00333                                         model_p->getVariable((*modeVarIDs)[j])->getDomain()->getValue((*currentValIDs)[j])));
    00334                 }
    00335                 if(!incrementCurrentValueArray(currentValIDs, modeDomainSizes, 0))
    00336                         allCombosExpanded = true;
    00337
    00338                 allModeComboRules.push_back(new ObsComboRule(ruleAssignments, numCombosObsAssigns, 2));
    00339         }
    00340
    00341
    00342         // Generate observation combination rules
    00343         allCombosExpanded = false;
    00344         while(!allCombosExpanded)
    00345         {
    00346                 ruleAssignments = new BaseModelAssignmentArray(true);
    00347                 for(j = 0; j < obsVarIDs->getLength(); j++)
    00348                 {
    00349                         ruleAssignments->pushBack(new BaseModelAssignment(model_p->getVariable((*obsVarIDs)[j]),
    00350                                         model_p->getVariable((*obsVarIDs)[j])->getDomain()->getValue((*currentObsValIDs)[j])));
    00351                 }
    00352                 if(!incrementCurrentValueArray(currentObsValIDs, obsDomainSizes, 0))
    00353                         allCombosExpanded = true;
    00354
    00355                 allObsComboRules.push_back(new Rule(ruleAssignments, 2));
    00356         }
    00357
    00358         obsTrigger = new RuleTrigger(allObsComboRules);
    00359
    00360
    00361         for(i = 0; i < relevantDissentIDs->getLength(); i++)
    00362         {
    00363                 ruleAssignments = new BaseModelAssignmentArray(true);
    00364                 const BaseModelAssignmentArray * conflict = dissents_vec[(*relevantDissentIDs)[i]]->getConflict();
    00365                 for(j=0; j<conflict->getLength(); j++)
    00366                 {
    00367                         ruleAssignments->pushBack(new BaseModelAssignment((*conflict)[j]->getVariable(), (*conflict)[j]->getValue()));
    00368                 }
    00369                 allRelevantConflictRules.push_back(new IndexedRule(ruleAssignments, (*relevantDissentIDs)[i], 2));
    00370         }
    00371         conflictTrigger = new RuleTrigger(allRelevantConflictRules);
    00372
    00373         // For each combination of mode variable assignments, determine how many consistant observation assignments
    00374         // there are
    00375         for(i = 0; i < allModeComboRules.size(); i++)
    00376         {
    00377                 // Determine which dissents correspond to this set of mode assignments
    00378                 for(j=0; j<allModeComboRules[i]->getAllAssignments()->getLength(); j++)
    00379                         conflictTrigger->loadAssignment((*allModeComboRules[i]->getAllAssignments())[j]->getVariable()->getUID(),
    00380                                         (*allModeComboRules[i]->getAllAssignments())[j]->getValue()->getUID());
    00381
    00382                 enabledConflictRules = conflictTrigger->getTriggeredRules();
    00383
    00384                 // Determine the number of inconsistent observations for the enabled conflicts
    00385                 for(k=0; k<enabledConflictRules.size(); k++)
    00386                 {
    00387                         for(j=0; j<dissents_vec[((IndexedRule *)enabledConflictRules[k])->getIndex()]->getAntecedentLength(); j++)
    00388                                 obsTrigger->loadAssignment(
    00389                                                 dissents_vec[((IndexedRule *)enabledConflictRules[k])->getIndex()]->getAntecedentVariableUID(j),
    00390                                                 dissents_vec[((IndexedRule *)enabledConflictRules[k])->getIndex()]->getAntecedentValueUID(j));
    00391                 }
    00392
    00393                 // count any observation combination that has 1 or greater satisfied observation assignments
    00394                 enabledObsRules = obsTrigger->getTriggeredRules(1);
    00395
    00396                 ((ObsComboRule *)allModeComboRules[i])->decrementBy(enabledObsRules.size());
    00397
    00398                 // Reset the triggers
    00399                 obsTrigger->reset();
    00400                 conflictTrigger->reset();
    00401         }
    00402
    00403         // Determine which rules are consistent with observations and not entailed or refuted
    00404         domainSize = 0;
    00405         for(i=0; i<allModeComboRules.size(); i++)
    00406         {
    00407                 if( ((ObsComboRule *)allModeComboRules[i])->getNumConsistentObsCombos() > 1)
    00408                 {
    00409                         if(debug > 2)
    00410                         {
    00411                                 for(j=0; j<allModeComboRules[i]->getAllAssignments()->getLength(); j++)
    00412                                 {
    00413                                         cout << (*allModeComboRules[i]->getAllAssignments())[j]->getVariable()->getUID() << ",";
    00414                                         cout << (*allModeComboRules[i]->getAllAssignments())[j]->getValue()->getUID() << " ";
    00415                                 }
    00416                                 cout << "with #: " << ((ObsComboRule *)allModeComboRules[i])->getNumConsistentObsCombos();
    00417                                 cout << endl << endl;
    00418                         }
    00419                         domainSize++;
    00420                         relevantObsRules.push_back((ObsComboRule *)allModeComboRules[i]);
    00421                 }
    00422         }
    00423         if(debug > 0)
    00424                 cout << "Number of required observation probabity rules: " << domainSize << endl;
    00425
    00426
    00427         // Check to see if any of the rules are independent
    00428         // Not necessary and takes a lot of time to run... doesnt work properly anyway.
    00429 //OM    cout << "Starting to check for independent rules..." << endl;
    00430 //OM    unsigned int numMatch, numNotMatch;
    00431 //OM    unsigned int theNumConsistent = 0;
    00432 //OM    bool foundMatch;
    00433 //OM    RuleTrigger * consistencyTrigger;
    00434 //OM    consistencyTrigger = new RuleTrigger(relevantObsRules, false);
    00435 //OM    //cout << *consistencyTrigger << endl;
    00436 //OM    for(i=0; i<modeVarIDs->getLength(); i++)
    00437 //OM    {
    00438 //OM            foundMatch = false;
    00439 //OM            allCombosExpanded = false;
    00440 //OM            while(!allCombosExpanded)
    00441 //OM            {
    00442 //OM                    numMatch = 0;
    00443 //OM                    numNotMatch = 0;
    00444 //OM                    theNumConsistent = 0;
    00445 //OM                    for(j=0; j<(*modeDomainSizes)[i]; j++) // See if every assignment has the same probability
    00446 //OM                    {
    00447 //OM                            for(k=0; k<modeVarIDs->getLength(); k++)
    00448 //OM                            {
    00449 //OM                                    if(k==i)
    00450 //OM                                            consistencyTrigger->loadAssignment((*modeVarIDs)[i], j);
    00451 //OM                                    else
    00452 //OM                                            consistencyTrigger->loadAssignment((*modeVarIDs)[k], (*currentObsValIDs)[k]);
    00453 //OM
    00454 //OM                            }
    00455 //OM                            enabledObsRules = consistencyTrigger->getTriggeredRules();
    00456 //OM                            if(enabledObsRules.size() > 1)
    00457 //OM                                    cerr << "<ProbRuleGenerator> ERROR: There is more than one enabled probability rule!" << endl;
    00458 //OM                            else if(enabledObsRules.size() == 1)
    00459 //OM                            {
    00460 //OM                                    if(numMatch == 0)
    00461 //OM                                    {
    00462 //OM                                            theNumConsistent = ((ObsComboRule *)enabledObsRules[0])->getNumConsistentObsCombos();
    00463 //OM                                            numMatch++;
    00464 //OM                                    }
    00465 //OM                                    else if(theNumConsistent == ((ObsComboRule *)enabledObsRules[0])->getNumConsistentObsCombos())
    00466 //OM                                            numMatch++;
    00467 //OM                                    else
    00468 //OM                                            numNotMatch++;
    00469 //OM                            }
    00470 //OM                            consistencyTrigger->reset();
    00471 //OM                    }
    00472 //OM                    if(numMatch > 1 && numNotMatch == 0)
    00473 //OM                    {
    00474 //OM                            cout << "*********** FOUND INDEPENDENT PAIR ***********" << endl;
    00475 //OM                            foundMatch = true;
    00476 //OM                            for(k=0; k<modeVarIDs->getLength(); k++)
    00477 //OM                            {
    00478 //OM                                    if(k==i)
    00479 //OM                                            cout << j << " ";
    00480 //OM                                    else
    00481 //OM                                            cout << (*currentObsValIDs)[i] << " ";
    00482 //OM
    00483 //OM                            }
    00484 //OM                            cout << endl << endl;
    00485 //OM                    }
    00486 //OM
    00487 //OM                    if(!incrementCurrentValueArray(currentValIDs, modeDomainSizes, 0, i))
    00488 //OM                            allCombosExpanded = true;
    00489 //OM
    00490 //OM            }
    00491 //OM            if(!foundMatch)
    00492 //OM            {
    00493 //OM                    cout << "Nothing for varUID# " << (*modeVarIDs)[i] << ", index # " << i << "..." << endl;
    00494 //OM            }
    00495 //OM    }
    00496 //OM    delete consistencyTrigger;
    00497
    00498         // Create the observation probability rules with the 1/m probability
    00499         for(i=0; i<relevantObsRules.size(); i++)
    00500                 groupsObservationProbs.push_back(new ObsProbRule(new BaseModelAssignmentArray(*relevantObsRules[i]->getAllAssignments()),
    00501                                                 1.0/(double)((ObsComboRule *)relevantObsRules[i])->getNumConsistentObsCombos()));
    00502
    00503         delete obsTrigger;
    00504         delete conflictTrigger;
    00505
    00506
    00507         delete modeDomainSizes;
    00508         delete modeVarIDs;
    00509         delete currentValIDs;
    00510
    00511         delete obsVarIDs;
    00512         delete obsDomainSizes;
    00513         delete currentObsValIDs;
    00514
    00515         while(allObsComboRules.size() > 0)
    00516         {
    00517                 delete allObsComboRules.back();
    00518                 allObsComboRules.pop_back();
    00519         }
    00520
    00521         return groupsObservationProbs;
    00522 }
    00523
    00524
    00525
    00526 bool
    00527 ProbRuleGenerator::incrementCurrentValueArray(
    00528         IntegerArray *& theCurrentValueIDs,
    00529         const IntegerArray * maxDomainSizes,
    00530         unsigned int index, int ignoreIndex) const
    00531 {
    00532         if(theCurrentValueIDs->getLength() != maxDomainSizes->getLength())
    00533         {
    00534                 cerr << "<ProbRuleGenerator> ERROR: Integer Arrays must be the same length to increment!" << endl;
    00535                 return false;
    00536         }
    00537         if(index >= theCurrentValueIDs->getLength())    // All the indices have overflow.. we're done.
    00538                 return false;
    00539
    00540         if(index == ignoreIndex)                        // Skip over this index
    00541                 return incrementCurrentValueArray(theCurrentValueIDs, maxDomainSizes, index+1);
    00542
    00543         (*theCurrentValueIDs)[index]++;
    00544         if((*theCurrentValueIDs)[index] >= (*maxDomainSizes)[index])
    00545         {
    00546                 (*theCurrentValueIDs)[index] = 0;
    00547                 return incrementCurrentValueArray(theCurrentValueIDs, maxDomainSizes, index+1);
    00548         }
    00549         return true;
    00550 }
    00551