コード例 #1
0
        public void HeavilyConstrainedMultipleCardinalityTest()
        {
            var p = new Problem("Heavily constrained multiple cardinality test");

            p.AddClause(2, 2, "w", "x", "y", "z");
            p.AddClause(1, 1, "x", "y");
            p.AddClause("w");
            for (int i = 0; i < 10; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.AreEqual(2, count);
                Assert.IsTrue(m.IsTrue("x") ^ m.IsTrue("y"));
                Assert.IsTrue(m.IsTrue("w"));
            }
        }
コード例 #2
0
        //Test wp under regular pseudo bool constrains
        public void BigConstrainTest5()
        {
            var p      = new Problem("cardinality");
            var clause = p.AddClause(1, 1, "w", "x", "y", "z");

            p.AddClause("w");
            p.AddClause(1, 1, "a", "b", "c");
            p.AddClause(1, 1, "e", "f");
            p.AddClause(1, 1, "e");
            for (int i = 0; i < 3; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.AreEqual("w", p.KeyOf(clause, 0).Name);
            }
        }
コード例 #3
0
        //Test if noise pushed up with Big constrains
        public void BigConstrainTest3()
        {
            var prob   = new Problem("bigCardinality3");
            var clause = prob.AddClause(10, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ll", "mm", "nn", "oo");

            prob.AddClause(20, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "p", "q", "r", "s", "t", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "pp", "qq", "rr", "ss", "tt");
            prob.AddClause(10, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "t", "u", "v", "w", "x", "y", "z", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo");

            for (int i = 0; i < 5; i++)
            {
                var m     = prob.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                //Assert.AreEqual(3, count);
                //Assert.IsTrue(m.IsTrue("w"));
                Assert.AreEqual("a", prob.KeyOf(clause, 0).Name);
            }
        }
コード例 #4
0
        //Test if noise pushed up with Big pseudo bool constrains
        public void BigConstrainTest4()
        {
            var prob   = new Problem("bigCardinality3");
            var clause = prob.AddClause(1, 1, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ab", "cd", "ac", "ad");

            prob.AddClause(1, 1, "ef", "eg", "hi", "hl", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo", "pp", "qq", "rr", "ss", "tt", "uu", "vv", "ww", "xx", "yy", "zz");
            prob.AddClause(1, 1, "aab", "abb", "ccd", "ddc", "aaa", "bbb", "ccc", "ddd", "eee", "fff", "ggg", "hhh", "iii", "jjj", "kkk", "lll", "mmm", "nnn", "ooo", "ppp", "qqq", "rrr", "sss", "ttt", "uuu", "vvv", "www", "xxx", "yyy", "zzz");
            //prob.AddClause(1, 1, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ab", "cd", "ac", "ad");
            //prob.AddClause(1, 1, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ab", "cd", "ac", "ad");
            for (int i = 0; i < 3; i++)
            {
                var m     = prob.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.AreEqual("a", prob.KeyOf(clause, 0).Name);
            }
        }
コード例 #5
0
        public void NegativeSolveTest()
        {
            var p = new Problem("Negative solve test");
            var positiveSolutionCount = 0;
            var negativeSolutionCount = 0;

            p.AddClause("x", Not("y"));  // x -> y
            p.AddClause(Not("x"), "y");  // y -> x
            // This should only have two models: both true or both false.
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                Assert.IsTrue(m.IsTrue("x") == m.IsTrue("y"));
                if (m.IsTrue("x"))
                {
                    positiveSolutionCount++;
                }
                else
                {
                    negativeSolutionCount++;
                }
            }
            Assert.IsTrue(positiveSolutionCount > 0, "Didn't generate any positive solutions!");
            Assert.IsTrue(negativeSolutionCount > 0, "Didn't generate any negative solutions!");
        }
コード例 #6
0
        public void ManualFluentTest()
        {
            var p          = new Problem("Manual fluent test");
            var after      = (Proposition)"after";
            var before     = (Proposition)"before";
            var activate   = (Proposition)"activate";
            var deactivate = (Proposition)"deactivate";

            // activate => after
            p.AddClause(after, Not(activate));
            // deactivate => not after
            p.AddClause(Not(after), Not(deactivate));
            // before => after | deactivate
            p.AddClause(Not(before), after, deactivate);
            // not before => not after | activate
            p.AddClause(before, Not(after), activate);
            // Can't simultaneously activate and deactivate
            p.AddClause(0, 1, activate, deactivate);

            for (int i = 0; i < 100; i++)
            {
                var s = p.Solve();
                if (s[after])
                {
                    Assert.IsTrue(s[before] || s[activate]);
                    Assert.IsFalse(s[deactivate]);
                }
                else
                {
                    Assert.IsTrue(!s[before] || s[deactivate]);
                    Assert.IsFalse(s[activate]);
                }
            }
        }
コード例 #7
0
        public void UnsatisfiableTest()
        {
            var p = new Problem("Unsatisfiable test");

            p.AddClause(2, 2, "w", "x", "y", "z");
            p.AddClause(1, 1, "x", "y");
            p.AddClause("w");
            p.AddClause("z");
            p.Solve();
            Assert.Fail();
        }
コード例 #8
0
        public void ConditionalTest2()
        {
            var p = new Problem("Compare with test 1");

            p.AddClause(2, 2, "a", "c");
            p.AddClause(1, 1, "b", "c");
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                Assert.IsFalse(m.IsTrue("b"));
            }
        }
コード例 #9
0
        public void PositiveSolveTest()
        {
            var p = new Problem("Positive solve test");

            p.AddClause("x", "y");
            p.AddClause("z");
            for (int i = 0; i < 100; i++)
            {
                var m = p.Solve();
                Assert.IsTrue(m.IsTrue("z"));
                Assert.IsTrue(m.IsTrue("x") || m.IsTrue("y"));
            }
        }
コード例 #10
0
        public void BiconditionalTest()
        {
            var p = new Problem(nameof(BiconditionalTest));

            // Assert a <-> b
            void IfAndOnlyIf(Proposition a, Proposition b)
            {
                // a -> b
                p.AddClause(Not(a), b);
                // b -> a
                p.AddClause(Not(b), a);
            }

            // This only has two models: a=b=c=d=true, and a=b=c=d=false
            // This is the best-case for the Propagation step in BooleanSolver.MakeRandomAssignment
            // because once it chooses the value of the first variable, it should immediately propagate
            // to all other variables.
            IfAndOnlyIf("a", "b");
            IfAndOnlyIf("b", "c");
            IfAndOnlyIf("c", "d");

            var trueCount = 0;

            for (var i = 0; i < 100; i++)
            {
                var m = p.Solve();

                // This shouldn't have used any flips because propagation in initialization
                // should always produce a valid model
                Assert.AreEqual(0, p.SolveFlips.Max);

                // Make sure all variables have the same value
                if (m["a"])
                {
                    trueCount++;
                    Assert.IsTrue(m["b"]);
                    Assert.IsTrue(m["c"]);
                }
                else
                {
                    Assert.IsFalse(m["b"]);
                    Assert.IsFalse(m["c"]);
                }
            }

            // True and false models ought to be more or less equally likely.
            Assert.IsTrue(trueCount > 40);
            Assert.IsTrue(trueCount < 60);
        }
コード例 #11
0
        public void ForcePreSettingVariablesTest()
        {
            var p      = new Problem("Force Extension hook test");
            var preset = true;

            void MaybeSetVarX(Problem _)
            {
                // ReSharper disable once AccessToModifiedClosure
                if (preset)
                {
                    p.SetPredeterminedValue("x", true, SATVariable.DeterminationState.Preinitialized);
                }
            }

            p.AddClause("x", "y");
            p.AddClause("x", "z");
            p.AddClause(Not("x"), "z");
            p.AddClause(Not("x"), "y");
            p.InitializeTruthAssignment += MaybeSetVarX;

            int numTrue  = 0;
            int numTests = 1000;

            for (int i = 0; i < numTests; i++)
            {
                var m = p.Solve();
                if (m.IsTrue("x"))
                {
                    numTrue++;
                }
            }
            Console.WriteLine(numTrue);
            Assert.IsTrue(numTrue == numTests);

            preset = false;

            numTrue  = 0;
            numTests = 1000;
            for (int i = 0; i < numTests; i++)
            {
                var m = p.Solve();
                if (m.IsTrue("x"))
                {
                    numTrue++;
                }
            }
            Console.WriteLine(numTrue);
            Assert.IsTrue(numTrue != numTests);
        }
コード例 #12
0
        public void PreSettingVariablesTest()
        {
            var p = new Problem("Extension hook test");

            p.AddClause("x", "y");
            p.AddClause("z");
            p.InitializeTruthAssignment += SetVarX;

            for (int i = 0; i < 100; i++)
            {
                var m = p.Solve();
                Assert.IsTrue(m.IsTrue("z"));
                Assert.IsTrue(m.IsTrue("x"));
            }
        }
コード例 #13
0
        public void UniqueTest()
        {
            var p = new Problem("Unique test");

            p.AddClause(1, 1, "w", "x", "y", "z");
            for (int i = 0; i < 100; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.AreEqual(1, count);
            }
        }
コード例 #14
0
        public void FixedCardinalityTest()
        {
            var p = new Problem("Fixed cardinality test");

            p.AddClause(2, 2, "w", "x", "y", "z");
            for (int i = 0; i < 100; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.AreEqual(2, count);
            }
        }
コード例 #15
0
        public void BoundedCardinalityTest()
        {
            var p = new Problem("Bounded cardinality test");

            p.AddClause(1, 3, "w", "x", "y", "z");
            for (int i = 0; i < 100; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }

                Assert.IsTrue(count >= 1 && count <= 3);
            }
        }
コード例 #16
0
        public void AddClauseTest()
        {
            var p      = new Problem("Add clause test");
            var clause = p.AddClause("x", "y");

            Assert.AreEqual("x", p.KeyOf(clause, 0).Name);
            Assert.AreEqual("y", p.KeyOf(clause, 1));
        }
コード例 #17
0
        public void NormalClause3()
        {
            var prob = new Problem("normal clause - more disjuncts and less clauses");

            prob.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ll", "mm", "nn", "oo");
            prob.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "p", "q", "r", "s", "t", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "pp", "qq", "rr", "ss", "tt");
            prob.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "t", "u", "v", "w", "x", "y", "z", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo");
            prob.AddClause("a", "b", "c", "d", "e", "f", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "s", "t", "u", "v", "w", "x", "y", "z", "ab", "cd", "ac", "ad");
            prob.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo", "y", "z", "ab", "cd", "ac", "ad");
            int[] flip = new int[1000];
            for (int i = 0; i < 1000; i++)
            {
                var m = prob.Solve();
                flip[i] = m.Problem.BooleanSolver.SolveFlips;
            }

            int average = flip.Sum() / flip.Length;

            Console.WriteLine(average); // average 0 flip 10 ms with propagation, 0 flip 7 ms w/o
        }
コード例 #18
0
        //Test wp in regular constrains
        public void CardinalityConstrainTest()
        {
            var p      = new Problem("cardinality");
            var clause = p.AddClause(2, 4, "w", "x", "y", "z");

            p.AddClause(0, 2, "x", "y");
            p.AddClause("w");
            p.AddClause(0, 3, "w", "x", "y");
            p.AddClause(0, 2, "x", "y");
            p.AddClause("w");
            for (int i = 0; i < 10; i++)
            {
                var m     = p.Solve();
                var count = 0;
                if (m.IsTrue("w"))
                {
                    count++;
                }
                if (m.IsTrue("x"))
                {
                    count++;
                }
                if (m.IsTrue("y"))
                {
                    count++;
                }
                if (m.IsTrue("z"))
                {
                    count++;
                }


                Assert.AreEqual("w", p.KeyOf(clause, 0).Name);
            }
        }
コード例 #19
0
        public void ConditionalTest1()
        {
            var p = new Problem("MultipleCardinality");

            p.QuantifyIf("a", 2, 2, "a", "c");
            p.AddClause(1, 1, "b", "c");
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                Assert.IsTrue(m.Model.Equals("{a, c}") | m.Model.Equals("{b}") | m.Model.Equals("{c}"));
                Assert.IsFalse(m.Model.Equals("{b, c}"));
            }
        }
コード例 #20
0
        public void RangeConstraintPropagationTest()
        {
            // This should come out of the initialization process with a valid model
            // So this shouldn't require any flips
            var p = new Problem("normal clauses mixed with large PBCs and conditional PBCs2");

            p.AddClause(3, 5, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m");

            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                Assert.AreEqual(0, m.Problem.BooleanSolver.SolveFlips);
            }
        }
コード例 #21
0
        public void ConditionalTest5()
        {
            var p = new Problem("MultipleCardinality2");

            p.AddClause(10, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ll", "mm", "nn", "oo");
            p.AddClause(20, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "p", "q", "r", "s", "t", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "pp", "qq", "rr", "ss", "tt");
            p.AddClause(10, 29, "a", "b", "c", "d", "e", "f", "g", "h", "i", "t", "u", "v", "w", "x", "y", "z", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo");
            p.AddClause(1, 1, "e");
            p.QuantifyIf("a", 2, 2, "a", "c");
            p.AddClause(1, 1, "b", "c");
            p.AddClause(1, 1, "d");
            for (int i = 0; i < 100; i++)
            {
                var m = p.Solve();
                Assert.IsTrue(m.IsTrue("e"));
                Assert.IsTrue(m.IsTrue("d"));
                Assert.IsFalse(m.Model.Equals("{e, c, b}"));
                Assert.IsFalse(m.Model.Equals("{e, c, b, d}"));
                Assert.IsFalse(m.Model.Equals("{e, a, b}"));
            }
        }
コード例 #22
0
        public void NormalAndPbc1()
        {
            var p = new Problem("normal clauses mixed with PBCs");

            p.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "ll", "mm", "nn", "oo");
            p.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "p", "q", "r", "s", "t", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "pp", "qq", "rr", "ss", "tt");
            p.AddClause("a", "b", "c", "d", "e", "f", "g", "h", "i", "t", "u", "v", "w", "x", "y", "z", "aa", "bb", "cc", "dd", "ee", "ff", "gg", "hh", "ii", "jj", "kk", "ll", "mm", "nn", "oo");
            p.AddClause(1, 1, "e", "f");
            p.AddClause("w");
            p.AddClause(1, 1, "a", "b", "c");
            int[] flip = new int[1000];
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                flip[i] = m.Problem.BooleanSolver.SolveFlips;
            }

            int average = flip.Sum() / flip.Length;

            Console.WriteLine(average); // average 1 flip 12ms with propagation, 1 flip 26ms w/o
        }
コード例 #23
0
        public void SkipPropagationTest()
        {
            var p = new Problem("Skip last test's propagation during initialization");

            p.AddClause("b", "c");
            p.AddClause("a", "d");
            p.AddClause("d", "c");
            p.AddClause("e", "c");
            p.AddClause("f", "g");
            p.AddClause("g", "c");
            p.AddClause("h", "k");
            p.AddClause("i", "c");
            p.AddClause("j", "g");
            p.AddClause("k", "c");
            p.AddClause("l", "c");
            p.AddClause("m", "c");
            p.AddClause("n", "r");
            p.AddClause(1, 1, "e", "f");
            p.AddClause("w");
            p.QuantifyIf("a", 2, 2, "a", "c");
            p.AddClause(1, 1, "b", "c");
            p.PropagateConstraintsDuringInitialization = false;
            int[] flip = new int[1000];
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                flip[i] = m.Problem.BooleanSolver.SolveFlips;
            }
            int average = flip.Sum() / flip.Length;

            p.Assert(average == 4);
        }
コード例 #24
0
        public void NormalAndPbc4()
        {
            var p = new Problem("normal clauses mixed with large PBCs and conditional PBCs2");

            p.AddClause("b", "c");
            p.AddClause("a", "d");
            p.AddClause("d", "c");
            p.AddClause("e", "c");
            p.AddClause("f", "g");
            p.AddClause("g", "c");
            p.AddClause("h", "k");
            p.AddClause("i", "c");
            p.AddClause("j", "g");
            p.AddClause("k", "c");
            p.AddClause("l", "c");
            p.AddClause("m", "c");
            p.AddClause("n", "r");
            p.AddClause(1, 1, "e", "f");
            p.AddClause("w");
            p.QuantifyIf("a", 2, 2, "a", "c");
            p.AddClause(1, 1, "b", "c");
            int[] flip = new int[1000];
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                flip[i] = m.Problem.BooleanSolver.SolveFlips;
            }

            int average = flip.Sum() / flip.Length;

            Console.WriteLine(average); // average 2 flip 10 ms w/ propagation, 4 flip 6 ms w/o
        }
コード例 #25
0
        public void NormalClause1()
        {
            var p = new Problem("normal clause - short and more clauses");

            p.AddClause("b", "c");
            p.AddClause("a", "c");
            p.AddClause("d", "c");
            p.AddClause("e", "c");
            p.AddClause("f", "c");
            p.AddClause("g", "c");
            p.AddClause("h", "c");
            p.AddClause("i", "c");
            p.AddClause("j", "c");
            p.AddClause("k", "c");
            p.AddClause("l", "c");
            p.AddClause("m", "c");
            p.AddClause("n", "c");
            p.AddClause("o", "c");
            p.AddClause("p", "c");
            p.AddClause("q", "c");
            p.AddClause("r", "c");
            p.AddClause("s", "c");
            p.AddClause("t", "c");
            p.AddClause("u", "c");
            p.AddClause("v", "c");
            p.AddClause("w", "c");
            p.AddClause("x", "c");
            p.AddClause("y", "c");
            p.AddClause("z", "c");
            p.AddClause("a", "b");
            p.AddClause("d", "b");
            int[] flip = new int[1000];
            for (int i = 0; i < 1000; i++)
            {
                var m = p.Solve();
                flip[i] = m.Problem.BooleanSolver.SolveFlips;
            }

            int average = flip.Sum() / flip.Length;

            Console.WriteLine(average);  // average 0 flip 6 mswith propagation, 1 flip 7 ms w/o
        }