Two-Level Minimization
LogicalOptimizer.Minimization provides exact and heuristic two-level minimization from a
truth-table specification: TruthTableMinimizer (Quine–McCluskey with covering-table
reductions and lower-bound-pruned branch-and-bound), CSV truth-table parsing, and
multi-output tables with shared cubes. Every example is asserted in
LogicalOptimizer.Tests/Documentation/DocExamplesTests.cs.
A function is given as its on-set: the minterm indices where the output is 1. Minterm
bit j is the value of variables[j], variables in the order you pass them.
Minimal SOP and POS
using LogicalOptimizer;
var variables = new[] { "a", "b", "c" };
var onSet = new[] { 3, 5, 6, 7 }; // 3-input majority: true when >= 2 inputs are 1
TruthTableMinimizer.MinimalSop(variables, onSet); // a & b | a & c | b & c
TruthTableMinimizer.MinimalPos(variables, onSet); // (b | c) & (a | c) & (a | b)
Proven-minimal status
MinimalSopWithStatus also reports whether the cover search completed (so the result is
provably minimal) or hit a work budget:
var (expression, provenMinimal) = TruthTableMinimizer.MinimalSopWithStatus(variables, onSet);
Console.WriteLine(provenMinimal); // True
Console.WriteLine(expression); // a & b | a & c | b & c
MinimalPosWithStatus is the product-of-sums analog — a minimal POS with the same
proven/budget flag — so the equivalent-CNF path can report its minimality independently
(surfaced on the facade as OptimizationResult.CnfMinimizationStatus).
See Operation contracts & statuses for what "provably minimal" means and its variable-count zone.
Don't-cares
An optional don't-care set lets the minimizer choose the cheapest cover:
// on-set {1}, don't-care {3}: the minimal cover is just "a".
TruthTableMinimizer.MinimalSop(new[] { "a", "b" }, new[] { 1 }, new[] { 3 }); // a
CSV truth tables
CsvTruthTableParser reads a CSV with variable columns and a Result / Output / Value
column. Values may be 0/1, true/false, t/f, yes/no, y/n.
// Straight to a DNF expression:
CsvTruthTableParser.ParseCsvToExpression("a,b,Result\n0,0,0\n0,1,1\n1,0,1\n1,1,0");
// (!a & b) | (a & !b)
// Rows absent from the CSV become don't-care minterms:
var partial = CsvTruthTableParser.ParseCsvToPartialTable("a,b,Result\n0,0,0\n0,1,1\n1,1,1");
partial.Variables; // [a, b]
partial.OnSet; // {2, 3}
partial.DontCareSet; // {1} (the missing a=1,b=0 row)
ParseCsvToPartialTable returns a PartialTruthTable (Variables / OnSet /
DontCareSet) you can feed straight into TruthTableMinimizer. Helpers
CsvTruthTableParser.LooksLikeCsv, ParseCsvFileToExpression and GenerateExampleCsv
round out the parser.
Multi-output tables with shared cubes
Several output columns are minimized together, sharing product terms where cheaper:
var table = CsvTruthTableParser.ParseCsvToMultiOutputTable(
"a,b,Sum,Carry\n0,0,0,0\n0,1,1,0\n1,0,1,0\n1,1,0,1",
new[] { "Sum", "Carry" });
table.Variables; // [a, b]
table.Outputs.Single(o => o.Name == "Sum").OnSet; // {1, 2}
table.Outputs.Single(o => o.Name == "Carry").OnSet; // {3}
MultiOutputTable exposes Variables and Outputs (each a MultiOutputFunction with
Name, OnSet, DontCareSet). On the CLI this is the --outputs=Sum,Carry flag (see
CLI usage).
Next steps
- Normal forms & transformations — the heuristic
MinimizeDnfHeuristicfor large covers. - Operation contracts & statuses — minimality statuses and zones.