public void FloatPredeteriminationTest() { var p = new Problem(nameof(GeneralSumConstraintTest)); var dom = new FloatDomain("unit", -1, 1); var x = (FloatVariable)dom.Instantiate("x"); var y = (FloatVariable)dom.Instantiate("y"); y.PredeterminedValue = 1; var sum = x + y; int spuriousHitCount = 0; for (int i = 0; i < 100; i++) { var v = Random.Float(-1, 1); x.PredeterminedValue = v; var s = p.Solve(); // Should always give us the predetermined value Assert.AreEqual(x.Value(s), v); Assert.AreEqual(sum.Value(s), v + 1); if (i % 2 == 0) { x.Reset(); s = p.Solve(); // Should almost never give us the formerly predetermined value // ReSharper disable CompareOfFloatsByEqualityOperator if (x.Value(s) == v || sum.Value(s) == v + 1) { // ReSharper restore CompareOfFloatsByEqualityOperator spuriousHitCount++; } } } Assert.IsTrue(spuriousHitCount < 3); }
public void AddNewPropositionsTest() { var p = new Problem(); p.Solve(); p["a"] = true; p.Solve(); }
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); }
public void UnaryFluentTest() { var domain = new[] { "a", "b", "c" }; var p = new Problem("Unary fluent test") { TimeHorizon = 10 }; var f = Fluent("f", domain, requireActivationSupport: false, requireDeactivationSupport: false); foreach (var d in domain) { for (int i = 0; i < 100; i++) { var s = p.Solve(); for (int t = 1; t < p.TimeHorizon; t++) { var before = f(d, t - 1); var after = f(d, t); var activate = Activate(before); var deactivate = Deactivate(before); if (s[after]) { Assert.IsTrue(s[before] || s[activate]); Assert.IsFalse(s[deactivate]); } else { Assert.IsTrue(!s[before] || s[deactivate]); Assert.IsFalse(s[activate]); } } } } }
public void ConditionalConstraintPropagationTest() { // 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"); var lits = new[] { "a", "b", "c" }.Select(s => (Literal)s).ToArray(); p.QuantifyIf("condition", 2, 3, lits); var enabledCount = 0; var tries = 10000; for (int i = 0; i < tries; i++) { var m = p.Solve(); var count = lits.Count(l => m[l]); var enabled = m["condition"]; if (enabled) { enabledCount++; } Assert.AreEqual(0, m.Problem.BooleanSolver.SolveFlips); Assert.IsTrue(!enabled || (count >= 2 && count <= 3)); } Assert.IsTrue(enabledCount > 0, "condition is never enabled"); Assert.IsTrue(enabledCount < tries, "condition is always enabled"); }
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); }
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 }
//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); } }
//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); } }
//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); } }
//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); } }
public void CompletionTest() { var p = new Problem("Completion test"); var s = (Proposition)"s"; var t = (Proposition)"t"; var u = (Proposition)"u"; var a = (Proposition)"a"; var b = (Proposition)"b"; var c = (Proposition)"c"; p.Assert( s <= (t & u), s <= (a & b), s <= c ); for (int i = 0; i < 100; i++) { var m = p.Solve(); Assert.AreEqual(m.IsTrue(s), (m.IsTrue(t) && m.IsTrue("u")) || (m.IsTrue(a) && m.IsTrue(b) || m.IsTrue(c))); } }
public void StructCharacterGeneratorTest() { var prog = new Problem("Struct character generator"); var characterType = new Struct("Character", new [] { new Member("race", null, "human", "electroid", "insectoid"), new Member("class", null, "fighter", "magic user", "cleric", "thief"), new Member("nationality", "race=human", "landia", "placeville", "cityburgh"), new Member("religion", "class=cleric", "monotheist", "pantheist", "lovecraftian", "dawkinsian") }, (p, v) => { // Electroids are atheists p.Inconsistent(v["race"] == "electroid", v["class"] == "cleric"); // Lovecraftianism is outlawed in Landia p.Inconsistent(v["nationality"] == "landia", v["religion"] == "lovecraftian"); // Insectoids believe in strict hierarchies p.Inconsistent(v["race"] == "insectoid", v["religion"] == "pantheist"); // Lovecraftianism is the state religion of cityburgh p.Inconsistent(v["nationality"] == "cityburgh", v["class"] == "cleric", v["religion"] != "lovecraftian"); }); prog.Instantiate("character", characterType); for (int i = 0; i < 100; i++) { Console.WriteLine(prog.Solve().Model); } }
public void LowTechCharacterGeneratorTest() { var prog = new Problem("Character generator"); prog.Assert("character"); // Races Partition("character", "human", "electroid", "insectoid"); // Classes Partition("character", "fighter", "magic user", "cleric", "thief"); prog.Inconsistent("electroid", "cleric"); // Nationalities of humans Partition("human", "landia", "placeville", "cityburgh"); // Religions of clerics Partition("cleric", "monotheist", "pantheist", "lovecraftian", "dawkinsian"); // Lovecraftianism is outlawed in Landia prog.Inconsistent("landia", "lovecraftian"); // Insectoids believe in strict hierarchies prog.Inconsistent("insectoid", "pantheist"); // Lovecraftianism is the state religion of cityburgh prog.Inconsistent("cityburgh", "cleric", Not("lovecraftian")); for (int i = 0; i < 100; i++) { Console.WriteLine(prog.Solve().Model); } }
public void NameTest() { string[] boys = { "john", "joe", "jim", "james" }; var bMenu = new Menu <string>("boys", boys); string[] girls = { "jenny", "jane", "janet", "julie" }; var gMenu = new Menu <string>("girls", girls); string[] surnames = { "jones", "johnson", "jefferson", "jackson" }; var sMenu = new Menu <string>("surnames", surnames); var p = new Problem("NameTest"); var firstName = new MenuVariable <string>("first", null, p); var lastName = (MenuVariable <string>)sMenu.Instantiate("last", p); var male = (Proposition)"male"; var female = (Proposition)"female"; p.Assert(firstName.In(bMenu) <= male); p.Assert(firstName.In(gMenu) <= female); p.Unique(male, female); for (int i = 0; i < 100; i++) { var m = p.Solve(); Console.WriteLine(m.Model); Assert.IsTrue(surnames.Contains(lastName.Value(m))); Assert.IsTrue((m[male] && boys.Contains(firstName.Value(m))) || (m[female] && girls.Contains(firstName.Value(m)))); } }
public void NonstrictTest() { var n = 8; var p = new Problem("induction test"); var pred = Predicate <int>("pred"); for (var i = 1; i < n - 1; i++) // cell set iff neighbor is set. { p.Assert( pred(i) <= pred(i - 1), pred(i) <= pred(i + 1) ); } // Solve it. for (int t = 0; t < 100; t++) { var m = p.Solve(); // This has 3 solutions: all false, all true, all but one end true, all but either end true. var c = m.Count(Range(0, n).Select(pred)); Assert.IsTrue(c == 0 || c >= n - 2); } }
public void SolutionUtilityTest() { var p = new Problem(nameof(SolutionUtilityTest)); var a = (Proposition)"a"; a.Utility = 1; var b = (Proposition)"b"; b.Utility = -1; var c = (Proposition)"c"; c.Utility = 1.5f; var d = (Proposition)"d"; d.Utility = 3.3f; var zero = (Proposition)"zeroUtility"; p.Quantify(1, 4, a, b, c, d, zero); for (int i = 0; i < 100; i++) { var s = p.Solve(); float U(Proposition prop) { if (s[prop]) { return(prop.Utility); } return(0); } Assert.IsTrue(Math.Abs(s.Utility - (U(a) + U(b) + U(c) + U(d) + U(zero))) < 0.0001f); } }
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!"); }
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]); } } }
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); } }
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")); } }
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); } }
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); } }
public void StoryTellerDemoTest() { var p = new Problem("Storyteller demo rebuild"); var cast = new[] { "red", "green", "blue" }; // characters don't have names and gender doesn't matter var rich = Predicate <string>("rich"); var caged = Predicate <string>("caged"); var hasSword = Predicate <string>("hasSword"); var evil = Predicate <string>("evil"); var kill = Predicate <string, string>("kill"); var loves = Predicate <string, string>("loves"); var dead = Predicate <string>("dead"); var tombstone = Predicate <string>("tombstone"); var someoneFree = (Proposition)"someoneFree"; // Panel 1 -> panel 2 foreach (var x in cast) { p.Assert( evil(x) == Not(rich(x)), caged(x) > rich(x), hasSword(x) == (rich(x) & Not(caged(x))), someoneFree <= Not(caged(x)), Not(kill(x, x)) ); // You can't kill multiple people p.AtMost(1, cast, y => kill(x, y)); foreach (var y in cast) { p.Assert( kill(x, y) > hasSword(x), kill(x, y) > evil(y) ); } } // Panel 2 -> panel 3 foreach (var x in cast) { foreach (var y in cast) { p.Assert( dead(y) <= kill(x, y), tombstone(x) <= (caged(x) & evil(y) & Not(dead(y))), tombstone(x) <= (Expression)Not(someoneFree), tombstone(x) <= dead(x) ); foreach (var z in cast) { p.Assert(loves(x, y) <= (caged(x) & kill(y, z))); } } } Console.WriteLine(p.Stats); for (int i = 0; i < 100; i++) { var s = p.Solve(); Console.WriteLine(s.Model); } }
public void SudokuTest() { var p = new Problem("Sudoku"); var digits = new[] { 1, 2, 3, 4, 5, 6, 7, 8, 9 }; var cell = Predicate <int, int, int>("cell"); foreach (var rank in digits) { foreach (var d in digits) { p.Unique(digits, row => cell(row, rank, d)); p.Unique(digits, column => cell(rank, column, d)); } } foreach (var row in digits) { foreach (var col in digits) { p.Unique(digits, d => cell(row, col, d)); } } for (int i = 0; i < 100; i++) { p.Solve(); } }
//[TestMethod] //public void InverseFloyWarshall10Test() //{ // // Make a random 5-node undirected graph with designated connected components. // // Computes transitive closure of using Floyd-Warshall // InverseFWTest("IFW10", new[] { "1", "2", "3", "4", "5", "6", "7", "8", "9", "10" }); //} //[TestMethod] //public void InverseFloyWarshall20Test() //{ // // Make a random 5-node undirected graph with designated connected components. // // Computes transitive closure of using Floyd-Warshall // InverseFWTest("IFW20", new[] // { // "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", // "11", "12", "13", "14", "15", "16", "17", "18", "19", "20" // }); //} private static void InverseFWTest(string name, string[] vertices) { var p = new Problem(name); var adjacent = Predicate <string, string>("adjacent"); var floyd = Predicate <string, string, int>("d"); // Inlines either adjacent or floyd, depending on k Proposition D(string v1, string v2, int k) => k == 0 ? adjacent(v1, v2) : floyd(v1, v2, k); for (int k = 1; k < vertices.Length; k++) { var vk = vertices[k]; foreach (var v1 in vertices) { foreach (var v2 in vertices) { p.Assert( D(v1, v2, k) <= D(v1, v2, k - 1), D(v1, v2, k) <= (D(v1, vk, k - 1) & D(vk, v2, k - 1)) ); } } } Proposition Connected(string v1, string v2) => D(v1, v2, vertices.Length - 1); // Now constrain its connectivity foreach (var v1 in vertices) { foreach (var v2 in vertices) { if (v1 == v2 || (v1 != "e" && v2 != "e")) { p.Assert(Connected(v1, v2)); } else { p.Assert(Not(Connected(v1, v2))); } } } p.Optimize(); for (int i = 0; i < 100; i++) { var s = p.Solve(); // a, b, c, d should be a connected component, e should be unconnected to anything but e foreach (var v1 in vertices) { foreach (var v2 in vertices) { Assert.IsTrue(s[Connected(v1, v2)] == (v1 == v2) || (v1 != "e" && v2 != "e")); } } } p.LogPerformanceData(); }
public void PredeterminedContradictionTest() { var p = new Problem(); p.Assert((Proposition)"a" > "b"); p["a"] = true; p["b"] = false; p.Solve(false); }
public void PartyGeneratorTest() { var prog = new Problem("Party generator"); var cast = new[] { "fred", "jenny", "sally" }; var character = Predicate <string>("character"); var human = Predicate <string>("human"); var electroid = Predicate <string>("electroid"); var insectoid = Predicate <string>("insectoid"); var fighter = Predicate <string>("fighter"); var magicUser = Predicate <string>("magic_user"); var cleric = Predicate <string>("cleric"); var thief = Predicate <string>("thief"); var landia = Predicate <string>("landia"); var placeville = Predicate <string>("placeville"); var cityburgh = Predicate <string>("cityburgh"); var monotheist = Predicate <string>("monotheist"); var pantheist = Predicate <string>("pantheist"); var lovecraftian = Predicate <string>("lovecraftian"); var dawkinsian = Predicate <string>("dawkinsian"); foreach (var who in cast) { prog.Assert(character(who)); // Races Partition(character(who), human(who), electroid(who), insectoid(who)); // Classes Partition(character(who), fighter(who), magicUser(who), cleric(who), thief(who)); prog.Inconsistent(electroid(who), cleric(who)); // Nationalities of humans Partition(human(who), landia(who), placeville(who), cityburgh(who)); // Religions of clerics Partition(cleric(who), monotheist(who), pantheist(who), lovecraftian(who), dawkinsian(who)); // Lovecraftianism is outlawed in Landia prog.Inconsistent(landia(who), lovecraftian(who)); // Insectoids believe in strict hierarchies prog.Inconsistent(insectoid(who), pantheist(who)); // Lovecraftianism is the state religion of cityburgh prog.Inconsistent(cityburgh(who), cleric(who), Not(lovecraftian(who))); } prog.AtMost(1, cast, fighter); prog.AtMost(1, cast, magicUser); prog.AtMost(1, cast, cleric); prog.AtMost(1, cast, thief); for (int i = 0; i < 100; i++) { Console.WriteLine(prog.Solve().Model); } }
public void QuantificationConstantFoldingSatisfiableTest3() { var p = new Problem("QuantificationConstantFoldingTest"); p.AtLeast(3, true, false, "a", "b"); for (int i = 0; i < 100; i++) { var s = p.Solve(); Assert.IsTrue(s["a"] && s["b"]); } }
public void QuantificationConstantFoldingSatisfiableTest() { var p = new Problem("QuantificationConstantFoldingTest"); p.Unique(true, false, "a", "b"); for (int i = 0; i < 100; i++) { var s = p.Solve(); Assert.IsFalse(s["a"] || s["b"]); } }