22 #ifndef QuadraticallyConstrainedSimpleSolver_hxx
23 #define QuadraticallyConstrainedSimpleSolver_hxx
30 template <
class ValueType>
33 m_WeightOfStandardDeviationTerm = 1.0;
34 oft = Cost_Function_rmse;
37 template <
class ValueType>
48 template <
class ValueType>
56 for (
unsigned int i = 0; i < m_AreaInOverlaps.rows(); i++)
58 if (s != i && m_AreaInOverlaps[s][i] > 0 && !marked[i])
68 template <
class ValueType>
73 const unsigned int n = m_AreaInOverlaps.cols();
76 itkExceptionMacro(<<
"Input area matrix has 0 elements");
79 bool inputMatricesAreValid =
true;
82 if ((n != m_AreaInOverlaps.rows()) || (n != m_MeanInOverlaps.cols()) || (n != m_MeanInOverlaps.rows()))
84 inputMatricesAreValid =
false;
88 if ((oft == Cost_Function_musig) || (oft == Cost_Function_weighted_musig) || (oft == Cost_Function_rmse))
90 if ((n != m_StandardDeviationInOverlaps.cols()) || (n != m_StandardDeviationInOverlaps.rows()))
92 inputMatricesAreValid =
false;
97 if (oft == Cost_Function_musig)
99 if ((n != m_MeanOfProductsInOverlaps.cols()) || (n != m_MeanOfProductsInOverlaps.rows()))
101 inputMatricesAreValid =
false;
105 if (!inputMatricesAreValid)
107 itkExceptionMacro(<<
"Input matrices must be square and have the same number of elements.");
125 template <
class ValueType>
133 if (oft == Cost_Function_mu)
137 if (oft == Cost_Function_musig)
141 if (oft == Cost_Function_weighted_musig)
143 w = (ValueType)m_WeightOfStandardDeviationTerm;
146 const unsigned int n = areas.cols();
151 for (
unsigned int i = 0; i < n; i++)
153 for (
unsigned int j = 0; j < n; j++)
158 for (
unsigned int k = 0; k < n; k++)
162 H[i][j] += areas[i][k] * (means[i][k] * means[i][k] + w * stds[i][k] * stds[i][k]);
163 K[i][j] += areas[i][k] * means[i][k];
164 L[i][j] += areas[i][k];
165 H_RMSE[i][j] += areas[i][k] * (means[i][k] * means[i][k] + stds[i][k] * stds[i][k]);
172 H[i][j] = -areas[i][j] * (means[i][j] * means[j][i] + w * stds[i][j] * stds[j][i]);
173 K[i][j] = -areas[i][j] * means[i][j];
174 L[i][j] = -areas[i][j];
175 H_RMSE[i][j] = -areas[i][j] * mops[i][j];
180 if (oft == Cost_Function_rmse)
191 template <
class ValueType>
195 unsigned int n = idx.size();
197 for (
unsigned int i = 0; i < n; i++)
199 for (
unsigned int j = 0; j < n; j++)
201 unsigned int mat_i = idx[i];
202 unsigned int mat_j = idx[j];
203 newMat[i][j] = mat[mat_i][mat_j];
212 template <
class ValueType>
219 if (m_AreaInOverlaps.max_value() == 0)
221 itkExceptionMacro(
"No overlap in images!");
225 unsigned int nbOfComponents = m_AreaInOverlaps.rows();
226 unsigned int nextVertex = 0;
227 std::vector<ListIndexType> connectedComponentsIndices;
228 std::vector<bool> markedVertices(nbOfComponents,
false);
229 bool allMarked =
false;
233 std::vector<bool> marked(nbOfComponents,
false);
234 DFS(marked, nextVertex);
238 for (
unsigned int i = 0; i < nbOfComponents; i++)
244 markedVertices[i] =
true;
246 else if (!markedVertices[i])
253 connectedComponentsIndices.push_back(list);
257 for (
unsigned int i = 0; i < nbOfComponents; i++)
258 if (!markedVertices[i])
263 m_OutputCorrectionModel.set_size(nbOfComponents);
264 m_OutputCorrectionModel.fill(itk::NumericTraits<ValueType>::One);
267 if (connectedComponentsIndices.size() > 1)
268 itkWarningMacro(
"Seems to be more that one group of overlapping images. Trying to harmonize groups separately.");
270 for (
unsigned int component = 0; component < connectedComponentsIndices.size(); component++)
274 const unsigned int n = list.size();
279 DoubleMatrixType sub_stdev = ExtractMatrix(m_StandardDeviationInOverlaps, list);
280 DoubleMatrixType sub_mOfPr = ExtractMatrix(m_MeanOfProductsInOverlaps, list);
283 DoubleMatrixType Q = GetQuadraticObjectiveMatrix(sub_areas, sub_means, sub_stdev, sub_mOfPr);
289 for (
unsigned int i = 0; i < n; i++)
291 double energy = sub_areas[i][i] * sub_means[i][i];
300 bool solv = vnl_solve_qp_with_non_neg_constraints(Q, g, A, b, x, 0.01);
303 for (
unsigned int i = 0; i < n; i++)
305 m_OutputCorrectionModel[list[i]] =
static_cast<double>(x[i]);
310 itkWarningMacro(
"vnl_solve_qp_with_non_neg_constraints failed for component #" << component);