[mlpack-git] master: error checking of initial matrices (4163316)

gitdub at big.cc.gt.atl.ga.us gitdub at big.cc.gt.atl.ga.us
Thu Mar 5 22:12:51 EST 2015


Repository : https://github.com/mlpack/mlpack

On branch  : master
Link       : https://github.com/mlpack/mlpack/compare/904762495c039e345beba14c1142fd719b3bd50e...f94823c800ad6f7266995c700b1b630d5ffdcf40

>---------------------------------------------------------------

commit 41633164908f29654296fcdd3cbf3379f54c0d35
Author: Stephen Tu <tu.stephenl at gmail.com>
Date:   Thu Jan 15 18:38:02 2015 -0800

    error checking of initial matrices


>---------------------------------------------------------------

41633164908f29654296fcdd3cbf3379f54c0d35
 src/mlpack/core/optimizers/sdp/primal_dual.cpp | 12 ++++++++++++
 src/mlpack/tests/sdp_primal_dual_test.cpp      | 27 +++++++++++++++++++++++++-
 2 files changed, 38 insertions(+), 1 deletion(-)

diff --git a/src/mlpack/core/optimizers/sdp/primal_dual.cpp b/src/mlpack/core/optimizers/sdp/primal_dual.cpp
index ef46bfc..f3b391c 100644
--- a/src/mlpack/core/optimizers/sdp/primal_dual.cpp
+++ b/src/mlpack/core/optimizers/sdp/primal_dual.cpp
@@ -36,11 +36,18 @@ PrimalDualSolver::PrimalDualSolver(const SDP& sdp,
     dualInfeasTol(1e-7),
     maxIterations(1000)
 {
+  arma::mat tmp;
+
   if (X0.n_rows != sdp.N() || X0.n_cols != sdp.N())
     Log::Fatal << "PrimalDualSolver::PrimalDualSolver(): "
       << "X0 needs to be square n x n matrix"
       << std::endl;
 
+  if (!arma::chol(tmp, X0))
+    Log::Fatal << "PrimalDualSolver::PrimalDualSolver(): "
+      << "X0 needs to be symmetric positive definite"
+      << std::endl;
+
   if (ysparse0.n_elem != sdp.NumSparseConstraints())
     Log::Fatal << "PrimalDualSolver::PrimalDualSolver(): "
       << "ysparse0 needs to have the same length as the number of sparse constraints"
@@ -55,6 +62,11 @@ PrimalDualSolver::PrimalDualSolver(const SDP& sdp,
     Log::Fatal << "PrimalDualSolver::PrimalDualSolver(): "
       << "Z0 needs to be square n x n matrix"
       << std::endl;
+
+  if (!arma::chol(tmp, Z0))
+    Log::Fatal << "PrimalDualSolver::PrimalDualSolver(): "
+      << "Z0 needs to be symmetric positive definite"
+      << std::endl;
 }
 
 static inline arma::mat
diff --git a/src/mlpack/tests/sdp_primal_dual_test.cpp b/src/mlpack/tests/sdp_primal_dual_test.cpp
index 534ea32..283f288 100644
--- a/src/mlpack/tests/sdp_primal_dual_test.cpp
+++ b/src/mlpack/tests/sdp_primal_dual_test.cpp
@@ -165,6 +165,7 @@ static void SolveMaxCutFeasibleSDP(const SDP& sdp)
   arma::vec ysparse0, ydense0;
   ydense0.set_size(0);
 
+  // strictly feasible starting point
   X0.eye(sdp.N(), sdp.N());
   ysparse0 = -1.1 * arma::vec(arma::sum(arma::abs(sdp.SparseC()), 0).t());
   Z0 = -Diag(ysparse0) + sdp.SparseC();
@@ -177,18 +178,42 @@ static void SolveMaxCutFeasibleSDP(const SDP& sdp)
   BOOST_REQUIRE(p.first);
 }
 
+static void SolveMaxCutPositiveSDP(const SDP& sdp)
+{
+  arma::mat X0, Z0;
+  arma::vec ysparse0, ydense0;
+  ydense0.set_size(0);
+
+  // infeasible, but positive starting point
+  X0.randu(sdp.N(), sdp.N());
+  X0 *= X0.t();
+  X0 += 0.01 * arma::eye<arma::mat>(sdp.N(), sdp.N());
+
+  ysparse0 = arma::randu<arma::vec>(sdp.NumSparseConstraints());
+  Z0.eye(sdp.N(), sdp.N());
+
+  PrimalDualSolver solver(sdp, X0, ysparse0, ydense0, Z0);
+
+  arma::mat X, Z;
+  arma::vec ysparse, ydense;
+  const auto p = solver.Optimize(X, ysparse, ydense, Z);
+  BOOST_REQUIRE(p.first);
+}
+
 /**
  * Start from a strictly feasible point
  */
-BOOST_AUTO_TEST_CASE(SmallMaxCutFeasibleSdp)
+BOOST_AUTO_TEST_CASE(SmallMaxCutSdp)
 {
   SDP sdp = ConstructMaxCutSDPFromLaplacian("r10.txt");
   SolveMaxCutFeasibleSDP(sdp);
+  SolveMaxCutPositiveSDP(sdp);
 
   UndirectedGraph g;
   UndirectedGraph::ErdosRenyiRandomGraph(g, 10, 0.3, true);
   sdp = ConstructMaxCutSDPFromGraph(g);
   SolveMaxCutFeasibleSDP(sdp);
+  SolveMaxCutPositiveSDP(sdp);
 }
 
 BOOST_AUTO_TEST_SUITE_END();



More information about the mlpack-git mailing list