OpenGM  2.3.x
Discrete Graphical Model Library
hqpbo.hxx
Go to the documentation of this file.
1 #pragma once
2 #ifndef OPENGM_HQPBO_HXX
3 #define OPENGM_HQPBO_HXX
4 
11 
13 #include "opengm/inference/fix-fusion/fusion-move.hpp"
14 
15 namespace opengm {
16 
21 template<class GM, class ACC>
22 class HQPBO : public Inference<GM, opengm::Minimizer>
23 {
24 public:
25  typedef GM GraphicalModelType;
26  typedef ACC AccumulationType;
31 
32  struct Parameter {};
33 
34  HQPBO(const GraphicalModelType&, Parameter = Parameter());
35  std::string name() const;
36  const GraphicalModelType& graphicalModel() const;
38  template<class VISITOR>
39  InferenceTermination infer(VISITOR &);
40  InferenceTermination arg(std::vector<LabelType>&, const size_t& = 1) const;
41  void setStartingPoint(typename std::vector<LabelType>::const_iterator begin );
42 private:
43  const GraphicalModelType& gm_;
44  ValueType constV_;
45  HigherOrderEnergy<ValueType, 10> hoe_;
46  std::vector<LabelType> conf_;
47  ValueType bound_;
48 };
49 
50 template<class GM, class ACC>
51 inline void
53 (
54  typename std::vector<typename HQPBO<GM,ACC>::LabelType>::const_iterator begin
55 ) {
56  for (size_t i=0; i<gm_.numberOfVariables(); ++i)
57  conf_[i] = *(begin+i);
58 }
59 
60 template<class GM,class ACC>
62 (
63  const GM & gm,
65 )
66  : gm_(gm), constV_(0.0), conf_(std::vector<LabelType>(gm.numberOfVariables(),0))
67 {
68  hoe_.AddVars(gm_.numberOfVariables());
69  for (IndexType f = 0; f < gm_.numberOfFactors(); ++f)
70  {
71  IndexType size = gm_[f].numberOfVariables();
72  const LabelType l0 = 0;
73  const LabelType l1 = 1;
74  if (size == 0)
75  {
76  constV_ += gm_[f](&l0);
77  continue;
78  }
79  else if (size == 1)
80  {
81  IndexType var = gm_[f].variableIndex(0);
82  const ValueType e0 = gm_[f](&l0);
83  const ValueType e1 = gm_[f](&l1);
84  hoe_.AddUnaryTerm(var, e1 - e0);
85  }
86  else
87  {
88  unsigned int numAssignments = 1 << size;
89  ValueType coeffs[numAssignments];
90  for (unsigned int subset = 1; subset < numAssignments; ++subset)
91  {
92  coeffs[subset] = 0;
93  }
94  // For each boolean assignment, get the clique energy at the
95  // corresponding labeling
96  LabelType cliqueLabels[size];
97  for (unsigned int assignment = 0; assignment < numAssignments; ++assignment)
98  {
99  for (unsigned int i = 0; i < size; ++i)
100  {
101  if (assignment & (1 << i))
102  {
103  cliqueLabels[i] = l1;
104  }
105  else
106  {
107  cliqueLabels[i] = l0;
108  }
109  }
110  ValueType energy = gm_[f](cliqueLabels);
111  for (unsigned int subset = 1; subset < numAssignments; ++subset)
112  {
113  if (assignment & ~subset)
114  {
115  continue;
116  }
117  else
118  {
119  int parity = 0;
120  for (unsigned int b = 0; b < size; ++b)
121  {
122  parity ^= (((assignment ^ subset) & (1 << b)) != 0);
123  }
124  coeffs[subset] += parity ? -energy : energy;
125  }
126  }
127  }
128  typename HigherOrderEnergy<ValueType, 10>::VarId vars[10];
129  for (unsigned int subset = 1; subset < numAssignments; ++subset)
130  {
131  int degree = 0;
132  for (unsigned int b = 0; b < size; ++b)
133  {
134  if (subset & (1 << b))
135  {
136  vars[degree++] = gm_[f].variableIndex(b);
137  }
138  }
139  std::sort(vars, vars + degree);
140  hoe_.AddTerm(coeffs[subset], degree, vars);
141  }
142  }
143  }
144 }
145 
146 template<class GM,class ACC>
147 inline std::string
149 {
150  return "HQPBO";
151 }
152 
153 template<class GM,class ACC>
154 inline const typename HQPBO<GM,ACC>::GraphicalModelType&
156 {
157  return gm_;
158 }
159 
160 template<class GM,class ACC>
163  EmptyVisitorType v;
164  return infer(v);
165 }
166 
167 template<class GM,class ACC>
168 template<class VISITOR>
170 HQPBO<GM,ACC>::infer(VISITOR & visitor)
171 {
172  visitor.begin(*this);
173  kolmogorov::qpbo::QPBO<ValueType> qr(gm_.numberOfVariables(), 0);
174  hoe_.ToQuadratic(qr);
175  qr.Solve();
176  IndexType numberOfChangedVariables = 0;
177  for (IndexType i = 0; i < gm_.numberOfVariables(); ++i)
178  {
179  int label = qr.GetLabel(i);
180  if (label == 0 )
181  {
182  conf_[i] = 0;
183  }
184  else if (label == 1)
185  {
186  conf_[i] = 1;
187  }
188  else
189  {
190  //conf_[i] = 0;
191  }
192  }
193  bound_ = constV_ + 0.5 * qr.ComputeTwiceLowerBound();
194  visitor.end(*this);
195  return NORMAL;
196 }
197 
198 template<class GM,class ACC>
201 (
202  std::vector<LabelType>& arg,
203  const size_t& n
204  ) const
205 {
206  if(n > 1) {
207  return UNKNOWN;
208  }
209  else {
210  arg.resize(gm_.numberOfVariables());
211  for (IndexType i = 0; i < gm_.numberOfVariables(); ++i)
212  arg[i] =conf_[i];
213  return NORMAL;
214  }
215 }
216 
217 
218 } // namespace opengm
219 
220 #endif // #ifndef OPENGM_HQPBO_HXX
std::string name() const
Definition: hqpbo.hxx:148
The OpenGM namespace.
Definition: config.hxx:43
GM GraphicalModelType
Definition: hqpbo.hxx:25
const GraphicalModelType & graphicalModel() const
Definition: hqpbo.hxx:155
visitors::VerboseVisitor< HQPBO< GM, ACC > > VerboseVisitorType
Definition: hqpbo.hxx:28
void setStartingPoint(typename std::vector< LabelType >::const_iterator begin)
set initial labeling
Definition: hqpbo.hxx:53
InferenceTermination arg(std::vector< LabelType > &, const size_t &=1) const
Definition: hqpbo.hxx:201
ACC AccumulationType
Definition: hqpbo.hxx:26
GraphicalModelType::IndexType IndexType
Definition: inference.hxx:40
visitors::TimingVisitor< HQPBO< GM, ACC > > TimingVisitorType
Definition: hqpbo.hxx:29
GraphicalModelType::ValueType ValueType
Definition: inference.hxx:41
Inference algorithm interface.
Definition: inference.hxx:34
HQPBO Algorithm .
Definition: hqpbo.hxx:22
HQPBO(const GraphicalModelType &, Parameter=Parameter())
Definition: hqpbo.hxx:62
GraphicalModelType::LabelType LabelType
Definition: inference.hxx:39
visitors::EmptyVisitor< HQPBO< GM, ACC > > EmptyVisitorType
Definition: hqpbo.hxx:30
OPENGM_GM_TYPE_TYPEDEFS
Definition: hqpbo.hxx:27
InferenceTermination
Definition: inference.hxx:24
InferenceTermination infer()
Definition: hqpbo.hxx:162