python-sat 1.8.dev13__tar.gz → 1.8.dev15__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of python-sat might be problematic. Click here for more details.
- {python-sat-1.8.dev13/python_sat.egg-info → python-sat-1.8.dev15}/PKG-INFO +1 -1
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/README.rst +10 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/allies/approxmc.py +16 -16
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/allies/unigen.py +13 -12
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/fm.py +3 -3
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/genhard.py +24 -23
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/hitman.py +5 -5
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/musx.py +1 -1
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/rc2.py +7 -7
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/__init__.py +1 -1
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/card.py +13 -12
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/engines.py +3 -3
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/formula.py +63 -48
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/pb.py +9 -8
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/solvers.py +119 -16
- {python-sat-1.8.dev13 → python-sat-1.8.dev15/python_sat.egg-info}/PKG-INFO +1 -1
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/python_sat.egg-info/SOURCES.txt +2 -1
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/pysolvers.cc +151 -39
- python-sat-1.8.dev13/tests/test_cnfplus.py → python-sat-1.8.dev15/tests/test_cnf.py +12 -1
- python-sat-1.8.dev15/tests/test_formula_unique.py +38 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/LICENSE.txt +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/MANIFEST.in +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/allies/__init__.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/bitwise.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/card.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/clset.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/common.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/itot.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/ladder.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/mto.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/pairwise.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/ptypes.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/pycard.cc +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/seqcounter.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/sortcard.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/cardenc/utils.hh +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/__init__.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/lbx.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/lsu.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/mcsls.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/models.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/optux.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/examples/usage.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/_fileio.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/_utils.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/pysat/process.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/python_sat.egg-info/dependency_links.txt +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/python_sat.egg-info/requires.txt +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/python_sat.egg-info/top_level.txt +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/requirements.txt +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/setup.cfg +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/setup.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/cadical103.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/cadical153.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/cadical170.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/cadical195.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/glucose30.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/glucose41.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/glucose421.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/lingeling.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/maplechrono.zip +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/maplecm.zip +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/maplesat.zip +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/mergesat3.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/minicard.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/minisat22.tar.gz +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/minisatgh.zip +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/cadical103.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/cadical153.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/cadical195.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/glucose30.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/glucose41.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/glucose421.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/gluecard30.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/gluecard41.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/lingeling.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/maplechrono.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/maplecm.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/maplesat.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/mergesat3.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/minicard.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/minisat22.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/patches/minisatgh.patch +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/solvers/prepare.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_accum_stats.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_atmost.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_atmost1.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_atmostk.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_boolengine.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_clausification.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_equals1.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_process.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_propagate.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_unique_model.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_unique_mus.py +0 -0
- {python-sat-1.8.dev13 → python-sat-1.8.dev15}/tests/test_warmstart.py +0 -0
|
@@ -348,6 +348,16 @@ publication, please, acknowledge that fact by citing PySAT:
|
|
|
348
348
|
doi = {10.1007/978-3-319-94144-8_26}
|
|
349
349
|
}
|
|
350
350
|
|
|
351
|
+
@inproceedings{itk-sat24,
|
|
352
|
+
author = {Alexey Ignatiev and Zi Li Tan and Christos Karamanos},
|
|
353
|
+
title = {Towards Universally Accessible {SAT} Technology},
|
|
354
|
+
booktitle = {SAT},
|
|
355
|
+
pages = {4:1--4:11},
|
|
356
|
+
year = {2024},
|
|
357
|
+
url = {https://doi.org/10.4230/LIPIcs.SAT.2024.16},
|
|
358
|
+
doi = {10.4230/LIPICS.SAT.2024.16},
|
|
359
|
+
}
|
|
360
|
+
|
|
351
361
|
To-Do
|
|
352
362
|
-----
|
|
353
363
|
|
|
@@ -47,17 +47,17 @@
|
|
|
47
47
|
The interface gives access to :class:`Counter`, which expects a formula in
|
|
48
48
|
:class:`.CNF` as input. Given a few additional (optional) arguments,
|
|
49
49
|
including a random seed, *tolerance factor* :math:`\\varepsilon`, and
|
|
50
|
-
*confidence* :math
|
|
50
|
+
*confidence* :math:`\\delta`, the class can be used to get an approximate
|
|
51
51
|
number of models of the formula, subject to the given tolerance factor and
|
|
52
52
|
confidence parameter.
|
|
53
53
|
|
|
54
|
-
Namely, given a CNF formula :math
|
|
55
|
-
as the exact number of models, and parameters
|
|
56
|
-
and :math
|
|
57
|
-
:math:`C`, which is an approximate number of
|
|
58
|
-
:math
|
|
59
|
-
:math:`\\textrm{Pr}
|
|
60
|
-
(1+\\varepsilon)
|
|
54
|
+
Namely, given a CNF formula :math:`\\mathcal{F}` with
|
|
55
|
+
:math:`\\#\\mathcal{F}` as the exact number of models, and parameters
|
|
56
|
+
:math:`\\varepsilon\\in(0,1]` and :math:`\\delta\\in[0,1)`, the counter
|
|
57
|
+
computes and reports a value :math:`C`, which is an approximate number of
|
|
58
|
+
models of :math:`\\mathcal{F}`, such that
|
|
59
|
+
:math:`\\textrm{Pr}\\left[\\frac{1}{1+\\varepsilon}\\#\\mathcal{F}\\leq
|
|
60
|
+
C\\leq (1+\\varepsilon)\\#\\mathcal{F}\\right]\\geq 1-\\delta`.
|
|
61
61
|
|
|
62
62
|
The implementation can be used as an executable (the list of available
|
|
63
63
|
command-line options can be shown using ``approxmc.py -h``) in the
|
|
@@ -131,13 +131,13 @@ class Counter(object):
|
|
|
131
131
|
models of the formula, subject to *tolerance factor* ``epsilon`` and
|
|
132
132
|
*confidence parameter* ``delta``.
|
|
133
133
|
|
|
134
|
-
Namely, given a CNF formula :math
|
|
135
|
-
:math:`\\varepsilon
|
|
136
|
-
computes and reports a value :math:`C` such that
|
|
137
|
-
:math:`\\textrm{Pr}
|
|
138
|
-
C
|
|
139
|
-
:math
|
|
140
|
-
:math
|
|
134
|
+
Namely, given a CNF formula :math:`\\mathcal{F}` and parameters
|
|
135
|
+
:math:`\\varepsilon\\in(0,1]` and :math:`\\delta\\in[0,1)`, the
|
|
136
|
+
counter computes and reports a value :math:`C` such that
|
|
137
|
+
:math:`\\textrm{Pr}\\left[\\frac{1}{1+\\varepsilon}\\#\\mathcal{F}\\leq
|
|
138
|
+
C\\leq (1+\\varepsilon)\\#\\mathcal{F}\\right]\\geq 1-\\delta`. Here,
|
|
139
|
+
:math:`\\#\\mathcal{F}` denotes the exact model count for formula
|
|
140
|
+
:math:`\\mathcal{F}`.
|
|
141
141
|
|
|
142
142
|
The ``formula`` argument can be left unspecified at this stage. In
|
|
143
143
|
this case, a user is expected to add all the relevant clauses using
|
|
@@ -241,7 +241,7 @@ class Counter(object):
|
|
|
241
241
|
of :class:`Counter` or through a series of calls to
|
|
242
242
|
:meth:`add_clause`, this method runs the ApproxMC counter with the
|
|
243
243
|
specified values of tolerance :math:`\\varepsilon` and confidence
|
|
244
|
-
:math
|
|
244
|
+
:math:`\\delta` parameters, as well as the random ``seed`` value,
|
|
245
245
|
and returns the number of models estimated.
|
|
246
246
|
|
|
247
247
|
A user may specify an argument ``projection``, which is a list of
|
|
@@ -50,20 +50,21 @@
|
|
|
50
50
|
The interface gives access to :class:`Sampler`, which expects a formula in
|
|
51
51
|
:class:`.CNF` as input. Given a few additional (optional) arguments,
|
|
52
52
|
including a random seed, *tolerance factor* :math:`\\varepsilon`,
|
|
53
|
-
*confidence* :math
|
|
54
|
-
parameter* :math
|
|
53
|
+
*confidence* :math:`\\delta` (to be used by ApproxMC), and *uniformity
|
|
54
|
+
parameter* :math:`\\kappa`, the class can be used to get apply
|
|
55
55
|
almost-uniform sampling and to obtain a requested number of samples as a
|
|
56
56
|
result, subject to the given tolerance factor and confidence parameter.
|
|
57
57
|
|
|
58
|
-
Namely, given a CNF formula :math
|
|
59
|
-
assignments (or models) denoted by :math:`sol(
|
|
60
|
-
:math:`\\varepsilon
|
|
61
|
-
:math:`y
|
|
62
|
-
\\textrm{ is
|
|
63
|
-
Almost-uniform sampling
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
\\
|
|
58
|
+
Namely, given a CNF formula :math:`\\mathcal{F}` with the set of
|
|
59
|
+
satisfying assignments (or models) denoted by :math:`sol(\\mathcal{F})`
|
|
60
|
+
and parameter :math:`\\varepsilon\\in(0,1]`, a uniform sampler outputs a
|
|
61
|
+
model :math:`y\\in sol(\\mathcal{F})` such that
|
|
62
|
+
:math:`\\textrm{Pr}\\left[y \\textrm{ is
|
|
63
|
+
output}\\right]=\\frac{1}{|sol(\\mathcal{F})|}`. Almost-uniform sampling
|
|
64
|
+
relaxes the uniformity guarantee and ensures that
|
|
65
|
+
:math:`\\frac{1}{(1+\\varepsilon)|sol(\\mathcal{F})|} \\leq
|
|
66
|
+
\\textrm{Pr}\\left[y \\textrm{ is output}\\right] \\leq
|
|
67
|
+
\\frac{1+\\varepsilon}{|sol(\\mathcal{F})|}`.
|
|
67
68
|
|
|
68
69
|
The implementation can be used as an executable (the list of available
|
|
69
70
|
command-line options can be shown using ``unigen.py -h``) in the
|
|
@@ -240,7 +241,7 @@ class Sampler(object):
|
|
|
240
241
|
of :class:`Sampler` or through a series of calls to
|
|
241
242
|
:meth:`add_clause`, this method runs the UniGen3 sampler with the
|
|
242
243
|
specified values of tolerance :math:`\\varepsilon`, confidence
|
|
243
|
-
:math
|
|
244
|
+
:math:`\\delta` parameters, and uniformity parameter :math:`kappa`
|
|
244
245
|
as well as the random ``seed`` value, and outputs a requested
|
|
245
246
|
number of samples.
|
|
246
247
|
|
|
@@ -386,12 +386,12 @@ class FM(object):
|
|
|
386
386
|
|
|
387
387
|
Otherwise (if the core contains more than one clause), every clause
|
|
388
388
|
:math:`c` of the core is *relaxed*. This means a new *relaxation
|
|
389
|
-
literal* is added to the clause, i.e. :math:`c
|
|
389
|
+
literal* is added to the clause, i.e. :math:`c\\gets c\\vee r`,
|
|
390
390
|
where :math:`r` is a fresh (unused) relaxation variable. After the
|
|
391
391
|
clauses get relaxed, a new cardinality encoding is added to the
|
|
392
392
|
formula enforcing the sum of the new relaxation variables to be not
|
|
393
|
-
greater than 1, :math
|
|
394
|
-
:math
|
|
393
|
+
greater than 1, :math:`\\sum_{c\\in\\phi}{r\\leq 1}`, where
|
|
394
|
+
:math:`\\phi` denotes the unsatisfiable core.
|
|
395
395
|
"""
|
|
396
396
|
|
|
397
397
|
if len(self.core) > 1:
|
|
@@ -129,7 +129,7 @@ class PHP(CNF, object):
|
|
|
129
129
|
"""
|
|
130
130
|
Generator of :math:`k` pigeonhole principle (:math:`k`-PHP) formulas.
|
|
131
131
|
Given integer parameters :math:`m` and :math:`k`, the :math:`k`
|
|
132
|
-
pigeonhole principle states that if :math:`k
|
|
132
|
+
pigeonhole principle states that if :math:`k\\cdot m+1` pigeons are
|
|
133
133
|
distributes by :math:`m` holes, then at least one hole contains more
|
|
134
134
|
than :math:`k` pigeons.
|
|
135
135
|
|
|
@@ -139,9 +139,9 @@ class PHP(CNF, object):
|
|
|
139
139
|
|
|
140
140
|
Assume that a Boolean variable :math:`x_{ij}` encodes that pigeon
|
|
141
141
|
:math:`i` resides in hole :math:`j`. Then a PHP formula can be seen as
|
|
142
|
-
a conjunction: :math:`\\bigwedge_{i=1}^{k
|
|
143
|
-
m+1}{\\textsf{AtLeast1}(x_{i1}
|
|
144
|
-
\\bigwedge_{j=1}^{m}{\\textsf{AtMost}k(x_{1j}
|
|
142
|
+
a conjunction: :math:`\\bigwedge_{i=1}^{k\\cdot
|
|
143
|
+
m+1}{\\textsf{AtLeast1}(x_{i1},\\ldots,x_{im})}\\wedge
|
|
144
|
+
\\bigwedge_{j=1}^{m}{\\textsf{AtMost}k(x_{1j},\\ldots,x_{k\\cdot
|
|
145
145
|
m+1,j})}`. Here each :math:`\\textsf{AtLeast1}` constraint forces every
|
|
146
146
|
pigeon to be placed into at least one hole while each
|
|
147
147
|
:math:`\\textsf{AtMost}k` constraint allows the corresponding hole to
|
|
@@ -204,16 +204,17 @@ class GT(CNF, object):
|
|
|
204
204
|
"""
|
|
205
205
|
Generator of ordering (or *greater than*, GT) principle formulas. Given
|
|
206
206
|
an integer parameter :math:`n`, the principle states that any partial
|
|
207
|
-
order on the set :math
|
|
208
|
-
|
|
209
|
-
Assume variable :math:`x_{ij}`, for :math:`i,j
|
|
210
|
-
the fact that :math:`i
|
|
211
|
-
\\neg{x_{ji}})` and :math:`(\\neg{x_{ij}}
|
|
212
|
-
x_{ik})` ensure that the relation
|
|
213
|
-
|
|
214
|
-
:math
|
|
215
|
-
|
|
216
|
-
:math:`
|
|
207
|
+
order on the set :math:`\\{1,2,\\ldots,n\\}` must have a maximal element.
|
|
208
|
+
|
|
209
|
+
Assume variable :math:`x_{ij}`, for :math:`i,j\\in[n],i\\neq j`,
|
|
210
|
+
denotes the fact that :math:`i \\succ j`. Clauses
|
|
211
|
+
:math:`(\\neg{x_{ij}} \\vee \\neg{x_{ji}})` and :math:`(\\neg{x_{ij}}
|
|
212
|
+
\\vee \\neg{x_{jk}} \\vee x_{ik})` ensure that the relation
|
|
213
|
+
:math:`\\succ` is anti-symmetric and transitive. As a result,
|
|
214
|
+
:math:`\\succ` is a partial order on :math:`[n]`. The additional
|
|
215
|
+
requirement that each element :math:`i` has a successor in
|
|
216
|
+
:math:`[n]\\setminus\\{i\\}` represented a clause :math:`(\\vee_{j
|
|
217
|
+
\\neq i}{x_{ji}})` makes the formula unsatisfiable.
|
|
217
218
|
|
|
218
219
|
GT formulas were originally conjectured [2]_ to be hard for resolution.
|
|
219
220
|
However, [5]_ proved the existence of a polynomial size resolution
|
|
@@ -276,18 +277,18 @@ class CB(CNF, object):
|
|
|
276
277
|
"""
|
|
277
278
|
Mutilated chessboard principle (CB). Given an integer :math:`n`, the
|
|
278
279
|
principle states that it is impossible to cover a chessboard of size
|
|
279
|
-
:math:`2n
|
|
280
|
+
:math:`2n\\cdot 2n` by domino tiles if two diagonally opposite corners
|
|
280
281
|
of the chessboard are removed.
|
|
281
282
|
|
|
282
283
|
Note that the chessboard has :math:`4n^2-2` cells. Introduce a Boolean
|
|
283
|
-
variable :math:`x_{ij}` for :math:`i,j
|
|
284
|
-
and :math:`j` are adjacent (no variables are introduced for
|
|
285
|
-
non-adjacent cells). CB formulas comprise clauses (1)
|
|
284
|
+
variable :math:`x_{ij}` for :math:`i,j\\in[4n^2-2]` s.t. cells
|
|
285
|
+
:math:`i` and :math:`j` are adjacent (no variables are introduced for
|
|
286
|
+
pairs of non-adjacent cells). CB formulas comprise clauses (1)
|
|
286
287
|
:math:`(\\neg{x_{ji} \\vee \\neg{x_{ki}}})` for every :math:`i,j \\neq
|
|
287
288
|
k` meaning that no more than one adjacent cell can be paired with the
|
|
288
|
-
current one; and (2) :math:`(\\vee_{j
|
|
289
|
-
\\forall i` enforcing that every cell :math:`i` should
|
|
290
|
-
at least one adjacent cell.
|
|
289
|
+
current one; and (2) :math:`(\\vee_{j \\in \\text{Adj}(i)}
|
|
290
|
+
{x_{ij}})\\,\\, \\forall i` enforcing that every cell :math:`i` should
|
|
291
|
+
be paired with at least one adjacent cell.
|
|
291
292
|
|
|
292
293
|
Clearly, since the two diagonal corners are removed, the formula is
|
|
293
294
|
unsatisfiable. Also note the following. Assuming that the number of
|
|
@@ -389,8 +390,8 @@ class PAR(CNF, object):
|
|
|
389
390
|
variables :math:`x_{ij},i \\neq j`. If variable :math:`x_{ij}` is
|
|
390
391
|
*true*, then there is an edge between nodes :math:`i` and :math:`j`.
|
|
391
392
|
The formula consists of the following clauses: :math:`(\\vee_{j \\neq
|
|
392
|
-
i}{x_{ij}})` for every :math:`i
|
|
393
|
-
\\vee \\neg{x_{kj}})` for all distinct :math:`i,j,k
|
|
393
|
+
i}{x_{ij}})` for every :math:`i\\in[2n+1]`, and :math:`(\\neg{x_{ij}}
|
|
394
|
+
\\vee \\neg{x_{kj}})` for all distinct :math:`i,j,k \\in [2n+1]`.
|
|
394
395
|
|
|
395
396
|
The parity principle is known to be hard for resolution [4]_.
|
|
396
397
|
|
|
@@ -35,14 +35,14 @@
|
|
|
35
35
|
by size) subset-minimal hitting enumeration.
|
|
36
36
|
|
|
37
37
|
The minimal hitting set problem is trivially formulated as a MaxSAT formula
|
|
38
|
-
in WCNF, as follows. Assume :math:`E
|
|
38
|
+
in WCNF, as follows. Assume :math:`E=\\{e_1,\\ldots,e_n\\}` to be a universe
|
|
39
39
|
of elements. Also assume there are :math:`k` sets to hit:
|
|
40
|
-
:math:`s_i
|
|
41
|
-
set :math:`s_i
|
|
42
|
-
clause :math:`(e_{i,1} \\vee
|
|
40
|
+
:math:`s_i=\\{e_{i,1},\\ldots,e_{i,j_i}\\}` s.t. :math:`e_{i,l}\\in E`. Every
|
|
41
|
+
set :math:`s_i=\\{e_{i,1},\\ldots,e_{i,j_i}\\}` is translated into a hard
|
|
42
|
+
clause :math:`(e_{i,1} \\vee \\ldots \\vee e_{i,j_i})`. This results in the
|
|
43
43
|
set of hard clauses having size :math:`k`. The set of soft clauses
|
|
44
44
|
comprises unit clauses of the form :math:`(\\neg{e_{j}})` s.t.
|
|
45
|
-
:math:`e_{j}
|
|
45
|
+
:math:`e_{j}\\in E`, each having weight 1.
|
|
46
46
|
|
|
47
47
|
Taking into account this problem formulation as MaxSAT, ordered hitting
|
|
48
48
|
enumeration is done with the use of the state-of-the-art MaxSAT solver
|
|
@@ -227,7 +227,7 @@ class MUSX(object):
|
|
|
227
227
|
|
|
228
228
|
Soft clauses are (de)activated using the standard MiniSat-like
|
|
229
229
|
assumptions interface [2]_. Each soft clause :math:`c` is augmented
|
|
230
|
-
with a selector literal :math:`s`, e.g. :math:`(c)
|
|
230
|
+
with a selector literal :math:`s`, e.g. :math:`(c) \\gets (c \\vee
|
|
231
231
|
\\neg{s})`. As a result, clause :math:`c` can be activated by
|
|
232
232
|
assuming literal :math:`s`. The over-approximation provided as an
|
|
233
233
|
input is specified as a list of selector literals for clauses in
|
|
@@ -695,8 +695,8 @@ class RC2(object):
|
|
|
695
695
|
"""
|
|
696
696
|
Detect and adapt intrinsic AtMost1 constraints. Assume
|
|
697
697
|
there is a subset of soft clauses
|
|
698
|
-
:math:`\\mathcal{S}'
|
|
699
|
-
:math
|
|
698
|
+
:math:`\\mathcal{S}'\\subseteq \\mathcal{S}` s.t.
|
|
699
|
+
:math:`\\sum_{c\\in\\mathcal{S}'}{c\\leq 1}`, i.e. at most
|
|
700
700
|
one of the clauses of :math:`\\mathcal{S}'` can be
|
|
701
701
|
satisfied.
|
|
702
702
|
|
|
@@ -709,7 +709,7 @@ class RC2(object):
|
|
|
709
709
|
unit-propagated to be false. Note that this method for
|
|
710
710
|
detection of AtMost1 constraints is *incomplete*, because
|
|
711
711
|
in general unit propagation does not suffice to test
|
|
712
|
-
whether or not :math:`\\mathcal{F}
|
|
712
|
+
whether or not :math:`\\mathcal{F}\\wedge l_i\\models
|
|
713
713
|
\\neg{l_j}`.
|
|
714
714
|
|
|
715
715
|
Each intrinsic AtMost1 constraint detected this way is
|
|
@@ -796,7 +796,7 @@ class RC2(object):
|
|
|
796
796
|
has cost at least :math:`|\\mathcal{S}'|-1` (assuming
|
|
797
797
|
*unweighted* MaxSAT). Furthermore, it is safe to replace
|
|
798
798
|
all clauses of :math:`\\mathcal{S}'` with a single soft
|
|
799
|
-
clause :math
|
|
799
|
+
clause :math:`\\sum_{c\\in\\mathcal{S}'}{c}`.
|
|
800
800
|
|
|
801
801
|
Here, input parameter ``am1`` plays the role of subset
|
|
802
802
|
:math:`\\mathcal{S}'` mentioned above. The procedure bumps
|
|
@@ -907,13 +907,13 @@ class RC2(object):
|
|
|
907
907
|
optimization* in [6]_.
|
|
908
908
|
|
|
909
909
|
Given a totalizer object ``tobj`` representing a sum of
|
|
910
|
-
some *relaxation* variables :math:`r
|
|
910
|
+
some *relaxation* variables :math:`r\\in R` that augment
|
|
911
911
|
soft clauses :math:`\\mathcal{C}_r`, the idea is to
|
|
912
912
|
increase the right-hand side of the sum (which is equal to
|
|
913
913
|
1 by default) as much as possible, reaching a value
|
|
914
914
|
:math:`k` s.t. formula
|
|
915
|
-
:math:`\\mathcal{H}
|
|
916
|
-
R}{r
|
|
915
|
+
:math:`\\mathcal{H}\\wedge\\mathcal{C}_r\\wedge(\\sum_{r\\in
|
|
916
|
+
R}{r\\leq k})` is still unsatisfiable while increasing it
|
|
917
917
|
further makes the formula satisfiable (here
|
|
918
918
|
:math:`\\mathcal{H}` denotes the hard part of the
|
|
919
919
|
formula).
|
|
@@ -68,10 +68,10 @@
|
|
|
68
68
|
pp. 129-134
|
|
69
69
|
|
|
70
70
|
A cardinality constraint is a constraint of the form:
|
|
71
|
-
:math
|
|
72
|
-
practical problem formulations. Note that the implementation of the
|
|
71
|
+
:math:`\\sum_{i=1}^n{x_i}\\leq k`. Cardinality constraints are ubiquitous
|
|
72
|
+
in practical problem formulations. Note that the implementation of the
|
|
73
73
|
pairwise, bitwise, and ladder encodings can only deal with AtMost1
|
|
74
|
-
constraints, e.g. :math
|
|
74
|
+
constraints, e.g. :math:`\\sum_{i=1}^n{x_i}\\leq 1`.
|
|
75
75
|
|
|
76
76
|
Access to all cardinality encodings can be made through the main class of
|
|
77
77
|
this module, which is :class:`.CardEnc`.
|
|
@@ -150,9 +150,9 @@ class EncType(object):
|
|
|
150
150
|
Note that while most of the encodings are produced as a list of
|
|
151
151
|
clauses, the "native" encoding of `MiniCard
|
|
152
152
|
<https://github.com/liffiton/minicard>`__ is managed as one clause.
|
|
153
|
-
Given an AtMostK constraint :math
|
|
154
|
-
encoding represents it as a pair ``[lits, k]``, where ``lits``
|
|
155
|
-
list of size ``n`` containing literals in the sum.
|
|
153
|
+
Given an AtMostK constraint :math:`\\sum_{i=1}^n{x_i\\leq k}`, the
|
|
154
|
+
native encoding represents it as a pair ``[lits, k]``, where ``lits``
|
|
155
|
+
is a list of size ``n`` containing literals in the sum.
|
|
156
156
|
"""
|
|
157
157
|
|
|
158
158
|
pairwise = 0
|
|
@@ -248,8 +248,8 @@ class CardEnc(object):
|
|
|
248
248
|
encoding=EncType.seqcounter):
|
|
249
249
|
"""
|
|
250
250
|
This method can be used for creating a CNF encoding of an AtMostK
|
|
251
|
-
constraint, i.e. of :math
|
|
252
|
-
shares the arguments and the return type with method
|
|
251
|
+
constraint, i.e. of :math:`\\sum_{i=1}^{n}{x_i}\\leq k`. The
|
|
252
|
+
method shares the arguments and the return type with method
|
|
253
253
|
:meth:`CardEnc.atleast`. Please, see it for details.
|
|
254
254
|
"""
|
|
255
255
|
|
|
@@ -310,9 +310,10 @@ class CardEnc(object):
|
|
|
310
310
|
encoding=EncType.seqcounter):
|
|
311
311
|
"""
|
|
312
312
|
This method can be used for creating a CNF encoding of an AtLeastK
|
|
313
|
-
constraint, i.e. of :math
|
|
314
|
-
takes 1 mandatory argument ``lits`` and 3 default arguments
|
|
315
|
-
specified: ``bound``, ``top_id``, ``vpool``, and
|
|
313
|
+
constraint, i.e. of :math:`\\sum_{i=1}^{n}{x_i}\\geq k`. The
|
|
314
|
+
method takes 1 mandatory argument ``lits`` and 3 default arguments
|
|
315
|
+
can be specified: ``bound``, ``top_id``, ``vpool``, and
|
|
316
|
+
``encoding``.
|
|
316
317
|
|
|
317
318
|
:param lits: a list of literals in the sum.
|
|
318
319
|
:param bound: the value of bound :math:`k`.
|
|
@@ -410,7 +411,7 @@ class CardEnc(object):
|
|
|
410
411
|
encoding=EncType.seqcounter):
|
|
411
412
|
"""
|
|
412
413
|
This method can be used for creating a CNF encoding of an EqualsK
|
|
413
|
-
constraint, i.e. of :math
|
|
414
|
+
constraint, i.e. of :math:`\\sum_{i=1}^{n}{x_i}= k`. The method
|
|
414
415
|
makes consecutive calls of both :meth:`CardEnc.atleast` and
|
|
415
416
|
:meth:`CardEnc.atmost`. It shares the arguments and the return type
|
|
416
417
|
with method :meth:`CardEnc.atleast`. Please, see it for details.
|
|
@@ -342,9 +342,9 @@ class LinearConstraint:
|
|
|
342
342
|
class ParityConstraint:
|
|
343
343
|
"""
|
|
344
344
|
A possible implementation of parity constraints. These are constraints
|
|
345
|
-
of the form :math:`l_1
|
|
346
|
-
each :math:`l_i` is a Boolean literal while :math:`b` is a
|
|
347
|
-
constant. The class is designed to exemplify the work with
|
|
345
|
+
of the form :math:`l_1 \\oplus l_2 \\oplus \\ldots \\oplus l_n = b`
|
|
346
|
+
where each :math:`l_i` is a Boolean literal while :math:`b` is a
|
|
347
|
+
Boolean constant. The class is designed to exemplify the work with
|
|
348
348
|
:class:`BooleanEngine`.
|
|
349
349
|
|
|
350
350
|
The implementation is pretty naive. It propagates a last unassigned
|