Fixed tabs and trailing whitespaces
[libdai.git] / src / lc.cpp
index 3aae934..6fcf73a 100644 (file)
@@ -1,6 +1,7 @@
-/*  Copyright (C) 2006-2008  Joris Mooij  [j dot mooij at science dot ru dot nl]
-    Radboud University Nijmegen, The Netherlands
-    
+/*  Copyright (C) 2006-2008  Joris Mooij  [joris dot mooij at tuebingen dot mpg dot de]
+    Radboud University Nijmegen, The Netherlands /
+    Max Planck Institute for Biological Cybernetics, Germany
+
     This file is part of libDAI.
 
     libDAI is free software; you can redistribute it and/or modify
@@ -24,7 +25,6 @@
 #include <map>
 #include <set>
 #include <dai/lc.h>
-#include <dai/diffs.h>
 #include <dai/util.h>
 #include <dai/alldai.h>
 
@@ -44,7 +44,7 @@ void LC::setProperties( const PropertySet &opts ) {
     assert( opts.hasKey("verbose") );
     assert( opts.hasKey("cavity") );
     assert( opts.hasKey("updates") );
-    
+
     props.tol = opts.getStringAs<double>("tol");
     props.maxiter = opts.getStringAs<size_t>("maxiter");
     props.verbose = opts.getStringAs<size_t>("verbose");
@@ -99,7 +99,7 @@ LC::LC( const FactorGraph & fg, const PropertySet &opts ) : DAIAlgFG(fg), _panca
 
     // create pancakes
     _pancakes.resize( nrVars() );
-   
+
     // create cavitydists
     for( size_t i=0; i < nrVars(); i++ )
         _cavitydists.push_back(Factor( delta(i) ));
@@ -120,7 +120,7 @@ LC::LC( const FactorGraph & fg, const PropertySet &opts ) : DAIAlgFG(fg), _panca
 }
 
 
-string LC::identify() const { 
+string LC::identify() const {
     return string(Name) + printProperties();
 }
 
@@ -135,7 +135,7 @@ double LC::CalcCavityDist (size_t i, const std::string &name, const PropertySet
     double maxdiff = 0;
 
     if( props.verbose >= 2 )
-        cout << "Initing cavity " << var(i) << "(" << delta(i).size() << " vars, " << nrStates(delta(i)) << " states)" << endl;
+        cerr << "Initing cavity " << var(i) << "(" << delta(i).size() << " vars, " << delta(i).nrStates() << " states)" << endl;
 
     if( props.cavity == Properties::CavityType::UNIFORM )
         Bi = Factor(delta(i));
@@ -166,15 +166,15 @@ double LC::InitCavityDists( const std::string &name, const PropertySet &opts ) {
     double tic = toc();
 
     if( props.verbose >= 1 ) {
-        cout << Name << "::InitCavityDists:  ";
+        cerr << Name << "::InitCavityDists:  ";
         if( props.cavity == Properties::CavityType::UNIFORM )
-            cout << "Using uniform initial cavity distributions" << endl;
+            cerr << "Using uniform initial cavity distributions" << endl;
         else if( props.cavity == Properties::CavityType::FULL )
-            cout << "Using full " << name << opts << "...";
+            cerr << "Using full " << name << opts << "...";
         else if( props.cavity == Properties::CavityType::PAIR )
-            cout << "Using pairwise " << name << opts << "...";
+            cerr << "Using pairwise " << name << opts << "...";
         else if( props.cavity == Properties::CavityType::PAIR2 )
-            cout << "Using pairwise(new) " << name << opts << "...";
+            cerr << "Using pairwise(new) " << name << opts << "...";
     }
 
     double maxdiff = 0.0;
@@ -183,10 +183,9 @@ double LC::InitCavityDists( const std::string &name, const PropertySet &opts ) {
         if( md > maxdiff )
             maxdiff = md;
     }
-    init();
 
     if( props.verbose >= 1 ) {
-        cout << Name << "::InitCavityDists used " << toc() - tic << " seconds." << endl;
+        cerr << Name << "::InitCavityDists used " << toc() - tic << " seconds." << endl;
     }
 
     return maxdiff;
@@ -194,8 +193,8 @@ double LC::InitCavityDists( const std::string &name, const PropertySet &opts ) {
 
 
 long LC::SetCavityDists( std::vector<Factor> &Q ) {
-    if( props.verbose >= 1 ) 
-        cout << Name << "::SetCavityDists:  Setting initial cavity distributions" << endl;
+    if( props.verbose >= 1 )
+        cerr << Name << "::SetCavityDists:  Setting initial cavity distributions" << endl;
     if( Q.size() != nrVars() )
         return -1;
     for( size_t i = 0; i < nrVars(); i++ ) {
@@ -204,7 +203,6 @@ long LC::SetCavityDists( std::vector<Factor> &Q ) {
         } else
             _cavitydists[i] = Q[i];
     }
-    init();
     return 0;
 }
 
@@ -216,19 +214,6 @@ void LC::init() {
                 _phis[i][I.iter].randomize();
             else
                 _phis[i][I.iter].fill(1.0);
-    for( size_t i = 0; i < nrVars(); i++ ) {
-        _pancakes[i] = _cavitydists[i];
-        
-        foreach( const Neighbor &I, nbV(i) ) {
-            _pancakes[i] *= factor(I);
-            if( props.updates == Properties::UpdateType::SEQRND )
-              _pancakes[i] *= _phis[i][I.iter];
-        }
-        
-        _pancakes[i].normalize();
-
-        CalcBelief(i);
-    }
 }
 
 
@@ -241,21 +226,21 @@ Factor LC::NewPancake (size_t i, size_t _I, bool & hasNaNs) {
     Factor A_I;
     for( VarSet::const_iterator k = Ivars.begin(); k != Ivars.end(); k++ )
         if( var(i) != *k )
-            A_I *= (_pancakes[findVar(*k)] * factor(I).inverse()).partSum( Ivars / var(i) );
+            A_I *= (_pancakes[findVar(*k)] * factor(I).inverse()).marginal( Ivars / var(i), false );
     if( Ivars.size() > 1 )
         A_I ^= (1.0 / (Ivars.size() - 1));
-    Factor A_Ii = (_pancakes[i] * factor(I).inverse() * _phis[i][_I].inverse()).partSum( Ivars / var(i) );
-    Factor quot = A_I.divided_by(A_Ii);
+    Factor A_Ii = (_pancakes[i] * factor(I).inverse() * _phis[i][_I].inverse()).marginal( Ivars / var(i), false );
+    Factor quot = A_I / A_Ii;
     if( props.damping != 0.0 )
         quot = (quot^(1.0 - props.damping)) * (_phis[i][_I]^props.damping);
 
-    piet *= quot.divided_by( _phis[i][_I] ).normalized();
+    piet *= quot / _phis[i][_I].normalized();
     _phis[i][_I] = quot.normalized();
 
     piet.normalize();
 
     if( piet.hasNaNs() ) {
-        cout << Name << "::NewPancake(" << i << ", " << _I << "):  has NaNs!" << endl;
+        cerr << Name << "::NewPancake(" << i << ", " << _I << "):  has NaNs!" << endl;
         hasNaNs = true;
     }
 
@@ -265,9 +250,9 @@ Factor LC::NewPancake (size_t i, size_t _I, bool & hasNaNs) {
 
 double LC::run() {
     if( props.verbose >= 1 )
-        cout << "Starting " << identify() << "...";
+        cerr << "Starting " << identify() << "...";
     if( props.verbose >= 2 )
-        cout << endl;
+        cerr << endl;
 
     double tic = toc();
     Diffs diffs(nrVars(), 1.0);
@@ -276,6 +261,20 @@ double LC::run() {
     if( md > _maxdiff )
         _maxdiff = md;
 
+    for( size_t i = 0; i < nrVars(); i++ ) {
+        _pancakes[i] = _cavitydists[i];
+
+        foreach( const Neighbor &I, nbV(i) ) {
+            _pancakes[i] *= factor(I);
+            if( props.updates == Properties::UpdateType::SEQRND )
+              _pancakes[i] *= _phis[i][I.iter];
+        }
+
+        _pancakes[i].normalize();
+
+        CalcBelief(i);
+    }
+
     vector<Factor> old_beliefs;
     for(size_t i=0; i < nrVars(); i++ )
         old_beliefs.push_back(belief(i));
@@ -287,7 +286,7 @@ double LC::run() {
             break;
         }
     if( hasNaNs ) {
-        cout << Name << "::run:  initial _pancakes has NaNs!" << endl;
+        cerr << Name << "::run:  initial _pancakes has NaNs!" << endl;
         return 1.0;
     }
 
@@ -304,7 +303,7 @@ double LC::run() {
         // Sequential updates
         if( props.updates == Properties::UpdateType::SEQRND )
             random_shuffle( update_seq.begin(), update_seq.end() );
-        
+
         for( size_t t=0; t < nredges; t++ ) {
             size_t i = update_seq[t].first;
             size_t _I = update_seq[t].second;
@@ -321,7 +320,7 @@ double LC::run() {
         }
 
         if( props.verbose >= 3 )
-            cout << Name << "::run:  maxdiff " << diffs.maxDiff() << " after " << _iters+1 << " passes" << endl;
+            cerr << Name << "::run:  maxdiff " << diffs.maxDiff() << " after " << _iters+1 << " passes" << endl;
     }
 
     if( diffs.maxDiff() > _maxdiff )
@@ -330,12 +329,12 @@ double LC::run() {
     if( props.verbose >= 1 ) {
         if( diffs.maxDiff() > props.tol ) {
             if( props.verbose == 1 )
-                cout << endl;
-                cout << Name << "::run:  WARNING: not converged within " << props.maxiter << " passes (" << toc() - tic << " seconds)...final maxdiff:" << diffs.maxDiff() << endl;
+                cerr << endl;
+                cerr << Name << "::run:  WARNING: not converged within " << props.maxiter << " passes (" << toc() - tic << " seconds)...final maxdiff:" << diffs.maxDiff() << endl;
         } else {
             if( props.verbose >= 2 )
-                cout << Name << "::run:  ";
-                cout << "converged in " << _iters << " passes (" << toc() - tic << " seconds)." << endl;
+                cerr << Name << "::run:  ";
+                cerr << "converged in " << _iters << " passes (" << toc() - tic << " seconds)." << endl;
         }
     }