graphicalmodeldecomposition.hxx

Go to the documentation of this file.
00001 #pragma once
00002 #ifndef OPENGM_GRAPHICALMODELDECOMPOSITION_HXX
00003 #define OPENGM_GRAPHICALMODELDECOMPOSITION_HXX
00004 
00005 #include <vector>
00006 #include <list>
00007 #include <set>
00008 #include <map>
00009 #include <limits>
00010 
00011 namespace opengm {
00012 
00014 
00015 class GraphicalModelDecomposition
00016 {
00017 public:
00018    class SubFactor {
00019    public:
00020       size_t subModelId_;
00021       size_t subFactorId_;
00022       std::vector<size_t> subIndices_;
00023       SubFactor(const size_t&, const size_t&, const std::vector<size_t>&); 
00024       SubFactor(const size_t&, const std::vector<size_t>&);
00025    };  
00026    typedef SubFactor EmptySubFactor;
00027 /*
00028    class EmptySubFactor {
00029    public:
00030       size_t subModelId_;
00031       size_t subFactorId_;
00032       std::vector<size_t> subIndices_;
00033       EmptySubFactor(const size_t&, const std::vector<size_t>&);
00034    }; 
00035 */
00036    class SubVariable {
00037    public:
00038       size_t subModelId_;
00039       size_t subVariableId_;
00040       SubVariable(const size_t&, const size_t&);
00041    };
00042 
00043    typedef std::list<SubFactor>      SubFactorListType;
00044    typedef std::list<SubFactor>      EmptySubFactorListType;
00045    typedef std::list<SubVariable>    SubVariableListType;
00046    
00047    GraphicalModelDecomposition();
00048    GraphicalModelDecomposition(const size_t numVariables, const size_t numFactors, const size_t numSubModels=0);
00049    size_t addSubModel();
00050    size_t addSubFactor(const size_t& subModel, const size_t& factorId, const std::vector<size_t>& subIndices);
00051    size_t addSubFactor(const size_t& subModel, const std::vector<size_t>& indices, const std::vector<size_t>& subIndices);
00052    size_t addSubVariable(const size_t& subModel, const size_t& variableId);
00053 
00054    void reorder(); 
00055    void complete();
00056    template <class GM> bool isValid(const GM&) const;
00057    const std::vector<SubFactorListType>& getFactorLists() const                             
00058       { return subFactorLists_; }
00059    const std::map<std::vector<size_t>,EmptySubFactorListType>& getEmptyFactorLists() const  
00060       { return emptySubFactorLists_; }
00061    const std::vector<SubVariableListType>& getVariableLists() const                         
00062       {return subVariableLists_; }
00063    size_t numberOfSubModels() const                   
00064       { return numberOfSubModels_; }
00065    size_t numberOfSubVariables(size_t subModel) const 
00066       { return numberOfSubVariables_[subModel]; }
00067    size_t numberOfSubFactors(size_t subModel) const   
00068       { return numberOfSubFactors_[subModel]; }
00069 
00070 private:
00071    size_t                                               numberOfVariables_;
00072    size_t                                               numberOfFactors_;
00073    size_t                                               numberOfSubModels_;
00074    std::vector<size_t>                                  numberOfSubFactors_;    //vectorsize = numberOfModels
00075    std::vector<size_t>                                  numberOfSubVariables_;  //vectorsize = numberOfModels
00076    std::vector<SubFactorListType>                       subFactorLists_;        //vectorsize = numberOfFactors
00077    std::vector<SubVariableListType>                     subVariableLists_;      //vectorsize = numberOfVariabels
00078    std::map<std::vector<size_t>,EmptySubFactorListType> emptySubFactorLists_;   //mapindex   = realFactorIndices
00079 };
00080 
00081 inline   
00082 GraphicalModelDecomposition::SubFactor::
00083 SubFactor
00084 (
00085    const size_t& sM, 
00086    const size_t& sF, 
00087    const std::vector<size_t>& sI
00088 )
00089 :  subModelId_(sM), 
00090    subFactorId_(sF), 
00091    subIndices_(sI)
00092 {}
00093    
00094 inline
00095 GraphicalModelDecomposition::SubFactor::
00096 SubFactor
00097 (
00098    const size_t& sM, 
00099    const std::vector<size_t>& sI
00100 )
00101 :  subModelId_(sM), 
00102    subIndices_(sI)
00103 {}
00104     
00105 inline
00106 GraphicalModelDecomposition::SubVariable::
00107 SubVariable
00108 (
00109    const size_t& sM, 
00110    const size_t& sV
00111 )
00112 :  subModelId_(sM), 
00113    subVariableId_(sV)
00114 {}
00115  
00116 inline
00117 GraphicalModelDecomposition::
00118 GraphicalModelDecomposition()
00119 {
00120    numberOfVariables_ = 0;
00121    numberOfFactors_   = 0;
00122    numberOfSubModels_ = 0;
00123 }
00124       
00125 inline   
00126 GraphicalModelDecomposition::
00127 GraphicalModelDecomposition
00128 (
00129    const size_t numNodes, 
00130    const size_t numFactors, 
00131    const size_t numSubModels
00132 )
00133 :  numberOfVariables_(numNodes), 
00134    numberOfFactors_(numFactors), 
00135    numberOfSubModels_(numSubModels)
00136 {
00137    numberOfSubFactors_.resize(numberOfSubModels_,0);
00138    numberOfSubVariables_.resize(numberOfSubModels_,0);
00139    subFactorLists_.resize(numberOfFactors_); 
00140    subVariableLists_.resize(numberOfVariables_);
00141 }
00142    
00143 inline size_t 
00144 GraphicalModelDecomposition::addSubModel()
00145 {  
00146    numberOfSubFactors_.push_back(0);
00147    numberOfSubVariables_.push_back(0);
00148    return numberOfSubModels_++;
00149 }
00150 
00151 inline size_t 
00152 GraphicalModelDecomposition::addSubFactor
00153 (
00154    const size_t& subModel, 
00155    const size_t& factorId, 
00156    const std::vector<size_t>& subIndices
00157 )
00158 {
00159    OPENGM_ASSERT(subModel < numberOfSubModels_);
00160    OPENGM_ASSERT(factorId < numberOfFactors_);
00161    if(!NO_DEBUG) {
00162       for(size_t i=0; i<subIndices.size(); ++i) {
00163          OPENGM_ASSERT(subIndices[i] < numberOfSubVariables_[subModel]); 
00164       }
00165    }
00166    subFactorLists_[factorId].push_back(SubFactor(subModel,numberOfSubFactors_[subModel],subIndices));
00167    return numberOfSubFactors_[subModel]++;
00168 }  
00169 
00170 inline size_t 
00171 GraphicalModelDecomposition::addSubFactor
00172 (
00173    const size_t& subModel, 
00174    const std::vector<size_t>& indices, 
00175    const std::vector<size_t>& subIndices
00176 )
00177 {
00178    OPENGM_ASSERT(subModel < numberOfSubModels_);
00179    if(!NO_DEBUG) {
00180       for(size_t i=0; i<subIndices.size(); ++i) {
00181          OPENGM_ASSERT(subIndices[i] < numberOfSubVariables_[subModel]); 
00182       }
00183    }
00184    emptySubFactorLists_[indices].push_back(SubFactor(subModel,subIndices));
00185    return numberOfSubFactors_[subModel]++;
00186 } 
00187 
00188 inline size_t 
00189 GraphicalModelDecomposition::addSubVariable
00190 (
00191    const size_t& subModel, 
00192    const size_t& variableId
00193 ) {
00194    OPENGM_ASSERT(subModel < numberOfSubModels_);
00195    OPENGM_ASSERT(variableId < numberOfVariables_);
00196    subVariableLists_[variableId].push_back(SubVariable(subModel,numberOfSubVariables_[subModel]));
00197    return  numberOfSubVariables_[subModel]++;
00198 }
00199 
00200 inline void GraphicalModelDecomposition::complete()
00201 { 
00202    SubVariableListType::iterator    it;
00203    SubFactorListType::iterator      it2; 
00204    EmptySubFactorListType::iterator it3;
00205 
00206    // build mapping: (subModel, subVariable) -> (realVariable)
00207    std::vector<std::vector<size_t> > subVariable2realVariable(numberOfSubModels_);
00208    for(size_t subModelId=0; subModelId<numberOfSubModels_; ++subModelId) {
00209       subVariable2realVariable[subModelId].resize(numberOfSubVariables_[subModelId],0);
00210    }
00211    for(size_t varId=0; varId<numberOfVariables_; ++varId) {
00212       for(it = subVariableLists_[varId].begin(); it!=subVariableLists_[varId].end();++it) {
00213          const size_t& subModelId    = (*it).subModelId_;
00214          const size_t& subVariableId = (*it).subVariableId_;
00215          subVariable2realVariable[subModelId][subVariableId] = varId; 
00216       }
00217    }
00218       
00219    // build mapping: (realVariable) -> (realUnaryFactor)
00220    std::vector<size_t> realVariable2realUnaryFactors(numberOfVariables_,std::numeric_limits<std::size_t>::max());
00221    for(size_t factorId=0; factorId<numberOfFactors_; ++factorId) {
00222       if(!subFactorLists_[factorId].empty() && subFactorLists_[factorId].front().subIndices_.size()==1) {
00223          const size_t& subModelId     = subFactorLists_[factorId].front().subModelId_;
00224          const size_t& subVariableId  = subFactorLists_[factorId].front().subIndices_[0];
00225          const size_t& realVariableId = subVariable2realVariable[subModelId][subVariableId];
00226          realVariable2realUnaryFactors[realVariableId] = factorId;
00227       }
00228    }
00229 
00230    // add missing unary Factors
00231    for(size_t varId=0; varId<numberOfVariables_; ++varId) {
00232       if(subVariableLists_[varId].size()>1) {
00233          std::vector<std::set<size_t> > required(numberOfSubModels_);
00234          // find Missing SubFactors 
00235          for(it = subVariableLists_[varId].begin(); it!=subVariableLists_[varId].end();++it) {
00236             const size_t& subModelId = (*it).subModelId_; 
00237             const size_t& subVariableId = (*it).subVariableId_;
00238             required[subModelId].insert(subVariableId);
00239          }
00240          if(realVariable2realUnaryFactors[varId] < std::numeric_limits<size_t>::max()) {
00241             const size_t& factorId = realVariable2realUnaryFactors[varId];
00242             // find included SubFactors
00243             for(it2 = subFactorLists_[factorId].begin(); it2!=subFactorLists_[factorId].end();++it2) {
00244                const size_t& subModelId = (*it2).subModelId_;
00245                const size_t& subVariableId = (*it2).subIndices_[0];
00246                required[subModelId].erase(subVariableId);
00247             }
00248             // add SubFactor that are still missing
00249             for(size_t subModelId=0; subModelId<numberOfSubModels_; ++subModelId) {
00250                for(std::set<size_t>::const_iterator setit=required[subModelId].begin(); setit!=required[subModelId].end(); setit++) {
00251                   const std::vector<size_t> subIndices(1,(*setit));
00252                   addSubFactor(subModelId, factorId, subIndices);
00253                }
00254             }     
00255          }
00256          else{
00257             // find included SubFactors
00258             std::vector<size_t> subIndices(1,varId);
00259             for(it3 = emptySubFactorLists_[subIndices].begin(); it3!=emptySubFactorLists_[subIndices].end();++it3) {
00260                const size_t& subModelId    = (*it3).subModelId_;
00261                const size_t& subVariableId = (*it3).subIndices_[0];
00262                required[subModelId].erase(subVariableId);
00263             }
00264             // add SubFactor that are still missing
00265             for(size_t subModelId=0; subModelId<numberOfSubModels_; ++subModelId) {
00266                for(std::set<size_t>::const_iterator setit=required[subModelId].begin(); setit!=required[subModelId].end(); setit++) {
00267                   const std::vector<size_t> indices(1,varId);
00268                   const std::vector<size_t> subIndices(1,(*setit));
00269                   addSubFactor(subModelId,indices, subIndices);
00270                }
00271             }       
00272          }
00273       }
00274    }
00275 }
00276 
00277 inline void GraphicalModelDecomposition::reorder()
00278 { 
00279    SubVariableListType::iterator it;
00280    SubFactorListType::iterator it2;
00281    EmptySubFactorListType::iterator it3;      
00282    std::map<std::vector<size_t>, EmptySubFactorListType>::iterator it4;
00283    
00284    std::vector<size_t> varCount(numberOfSubModels_,0);
00285    std::vector<std::vector<size_t> > subVarMap(numberOfSubModels_);
00286    for(size_t subModel=0; subModel<numberOfSubModels_; ++subModel) {
00287       subVarMap[subModel].resize(numberOfSubVariables_[subModel],0);
00288    }
00289 
00290    // re-order SubVariableIds
00291    for(size_t varId=0; varId<numberOfVariables_; ++varId) {
00292       for(it = subVariableLists_[varId].begin(); it!=subVariableLists_[varId].end();++it) {
00293          const size_t& subModelId    = (*it).subModelId_;
00294          const size_t& subVariableId = (*it).subVariableId_;
00295          subVarMap[subModelId][subVariableId] = varCount[subModelId];
00296          (*it).subVariableId_ =  varCount[subModelId]++;
00297       }
00298    }
00299 
00300    // reset FactorSubIndices
00301    for(size_t factorId=0; factorId<numberOfFactors_; ++factorId) {
00302       for(it2 = subFactorLists_[factorId].begin(); it2!=subFactorLists_[factorId].end();++it2) {
00303          const size_t& subModelId = (*it2).subModelId_;
00304          for(size_t i=0; i<(*it2).subIndices_.size();++i) {
00305             (*it2).subIndices_[i] = subVarMap[subModelId][(*it2).subIndices_[i]];
00306          }
00307          for(size_t i=1; i<(*it2).subIndices_.size();++i) {
00308             OPENGM_ASSERT((*it2).subIndices_[i-1] < (*it2).subIndices_[i]);
00309          }
00310       }
00311    } 
00312    for(it4=emptySubFactorLists_.begin() ; it4 != emptySubFactorLists_.end(); it4++ ) {
00313       for(it3 = (*it4).second.begin(); it3!=(*it4).second.end();++it3) {
00314          const size_t& subModelId = (*it3).subModelId_;
00315          for(size_t i=0; i<(*it3).subIndices_.size();++i) {
00316             (*it3).subIndices_[i] = subVarMap[subModelId][(*it3).subIndices_[i]];
00317          }
00318          for(size_t i=1; i<(*it3).subIndices_.size();++i) {
00319             OPENGM_ASSERT((*it3).subIndices_[i-1] < (*it3).subIndices_[i]);
00320          }
00321       }
00322    }
00323 }
00324 
00325 template <class GM>
00326 bool GraphicalModelDecomposition::isValid(const GM& gm) const
00327 {
00328    OPENGM_ASSERT(subVariableLists_.size() == gm.numberOfVariables());
00329    OPENGM_ASSERT(subFactorLists_.size() == gm.numberOfFactors());
00330    if(!NO_DEBUG) {
00331       for(size_t i=0; i<gm.numberOfVariables(); ++i) {
00332          OPENGM_ASSERT(subVariableLists_[i].size() > 0);
00333       }
00334    }
00335    for(size_t i=0; i<gm.numberOfFactors(); ++i) {
00336       OPENGM_ASSERT(subFactorLists_[i].size() > 0);
00337       for(SubFactorListType::const_iterator it=subFactorLists_[i].begin() ; it != subFactorLists_[i].end(); it++ ) {
00338          OPENGM_ASSERT((*it).subIndices_.size() == gm[i].numberOfVariables());
00339          // check consistency of SubIndices of SubFactors
00340          for(size_t j=0; j<gm[i].numberOfVariables(); ++j) {
00341             const SubVariableListType &list = subVariableLists_[gm[i].variableIndex(j)];
00342             bool check = false;
00343             for(SubVariableListType::const_iterator it2=list.begin() ; it2 != list.end(); it2++ ) {
00344                if(((*it2).subModelId_ == (*it).subModelId_) && ((*it2).subVariableId_ == (*it).subIndices_[j])) {
00345                   check = true;
00346                }
00347             }
00348             OPENGM_ASSERT(check);
00349          }
00350       }
00351    }
00352 
00353    bool ret = true; 
00354    if(subVariableLists_.size() != gm.numberOfVariables()) { 
00355       ret = false; 
00356    }
00357    if(subFactorLists_.size() != gm.numberOfFactors()) { 
00358       ret = false; 
00359    }
00360    for(size_t i=0; i<gm.numberOfVariables(); ++i) {
00361       if(subVariableLists_[i].size()==0) {
00362          ret = false;
00363       }
00364    } 
00365    for(size_t i=0; i<gm.numberOfFactors(); ++i) {
00366       if(subFactorLists_[i].size()==0) {
00367          ret = false;
00368       } 
00369       for(SubFactorListType::const_iterator it=subFactorLists_[i].begin() ; it != subFactorLists_[i].end(); it++ ) {
00370          if((*it).subIndices_.size() != gm[i].numberOfVariables()) {
00371             ret = false;
00372          } 
00373          //Check Consistency of SubIndices of SubFactors
00374          //This might be very timeconsuming
00375          /*
00376          for(size_t j=0; j<gm[i].numberOfVariables(); ++j) {
00377             const SubVariableListType &list = subVariableLists_[gm[i].variableIndex(j)];
00378             bool check = false;
00379             for(SubVariableListType::const_iterator it2=list.begin() ; it2 != list.end(); it2++ ) {
00380                if( (*it2).subModelId == (*it).subModelId && (*it2).subVariableId == (*it).subIndices_[j]) {
00381                   check = true;
00382                }
00383             }
00384             if(!check) {ret=false;}
00385          }
00386          */
00387       }
00388    }
00389    return ret;
00390 }
00391 
00393 
00394 } // namespace opengm
00395 
00396 #endif // #ifndef OPENGM_GRAPHICALMODELDECOMPOSITION_HXX
00397 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
Generated on Mon Jun 17 16:31:03 2013 for OpenGM by  doxygen 1.6.3