python-sat 1.8.dev25__cp310-cp310-musllinux_1_2_x86_64.whl

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.
Files changed (50) hide show
  1. pycard.cpython-310-x86_64-linux-gnu.so +0 -0
  2. pysat/__init__.py +24 -0
  3. pysat/_fileio.py +209 -0
  4. pysat/_utils.py +58 -0
  5. pysat/allies/__init__.py +0 -0
  6. pysat/allies/approxmc.py +385 -0
  7. pysat/allies/unigen.py +435 -0
  8. pysat/card.py +802 -0
  9. pysat/engines.py +1302 -0
  10. pysat/examples/__init__.py +0 -0
  11. pysat/examples/bbscan.py +663 -0
  12. pysat/examples/bica.py +691 -0
  13. pysat/examples/fm.py +527 -0
  14. pysat/examples/genhard.py +516 -0
  15. pysat/examples/hitman.py +653 -0
  16. pysat/examples/lbx.py +638 -0
  17. pysat/examples/lsu.py +496 -0
  18. pysat/examples/mcsls.py +610 -0
  19. pysat/examples/models.py +189 -0
  20. pysat/examples/musx.py +344 -0
  21. pysat/examples/optux.py +710 -0
  22. pysat/examples/primer.py +620 -0
  23. pysat/examples/rc2.py +1858 -0
  24. pysat/examples/usage.py +63 -0
  25. pysat/formula.py +5619 -0
  26. pysat/pb.py +463 -0
  27. pysat/process.py +363 -0
  28. pysat/solvers.py +7591 -0
  29. pysolvers.cpython-310-x86_64-linux-gnu.so +0 -0
  30. python_sat-1.8.dev25.data/scripts/approxmc.py +385 -0
  31. python_sat-1.8.dev25.data/scripts/bbscan.py +663 -0
  32. python_sat-1.8.dev25.data/scripts/bica.py +691 -0
  33. python_sat-1.8.dev25.data/scripts/fm.py +527 -0
  34. python_sat-1.8.dev25.data/scripts/genhard.py +516 -0
  35. python_sat-1.8.dev25.data/scripts/lbx.py +638 -0
  36. python_sat-1.8.dev25.data/scripts/lsu.py +496 -0
  37. python_sat-1.8.dev25.data/scripts/mcsls.py +610 -0
  38. python_sat-1.8.dev25.data/scripts/models.py +189 -0
  39. python_sat-1.8.dev25.data/scripts/musx.py +344 -0
  40. python_sat-1.8.dev25.data/scripts/optux.py +710 -0
  41. python_sat-1.8.dev25.data/scripts/primer.py +620 -0
  42. python_sat-1.8.dev25.data/scripts/rc2.py +1858 -0
  43. python_sat-1.8.dev25.data/scripts/unigen.py +435 -0
  44. python_sat-1.8.dev25.dist-info/METADATA +45 -0
  45. python_sat-1.8.dev25.dist-info/RECORD +50 -0
  46. python_sat-1.8.dev25.dist-info/WHEEL +5 -0
  47. python_sat-1.8.dev25.dist-info/licenses/LICENSE.txt +21 -0
  48. python_sat-1.8.dev25.dist-info/top_level.txt +3 -0
  49. python_sat.libs/libgcc_s-0cd532bd.so.1 +0 -0
  50. python_sat.libs/libstdc++-5d72f927.so.6.0.33 +0 -0
pysat/pb.py ADDED
@@ -0,0 +1,463 @@
1
+ #!/usr/bin/env python
2
+ #-*- coding:utf-8 -*-
3
+ ##
4
+ ## pb.py
5
+ ##
6
+ ## Created on: Mar 13, 2019
7
+ ## Author: Alexey S. Ignatiev
8
+ ## E-mail: aignatiev@ciencias.ulisboa.pt
9
+ ##
10
+
11
+ """
12
+ ===============
13
+ List of classes
14
+ ===============
15
+
16
+ .. autosummary::
17
+ :nosignatures:
18
+
19
+ EncType
20
+ PBEnc
21
+
22
+ ==================
23
+ Module description
24
+ ==================
25
+
26
+ .. note::
27
+
28
+ Functionality of this module is available only if the `PyPBLib`
29
+ package is installed, e.g. from PyPI:
30
+
31
+ .. code-block::
32
+
33
+ $ pip install pypblib
34
+
35
+ This module provides access to the basic functionality of the `PyPBLib
36
+ library <https://pypi.org/project/pypblib/>`__ developed by the `Logic
37
+ Optimization Group <http://ulog.udl.cat/>`__ of the University of Lleida.
38
+ PyPBLib provides a user with an extensive Python API to the well-known
39
+ `PBLib library <http://tools.computational-logic.org/content/pblib.php>`__
40
+ [1]_. Note the PyPBLib has a number of `additional features
41
+ <http://hardlog.udl.cat/static/doc/pypblib/html/index.html>`__ that cannot
42
+ be accessed through PySAT *at this point*. (One concrete example is a
43
+ range of cardinality encodings, which clash with the internal
44
+ :mod:`pysat.card` module.) If a user needs some functionality of PyPBLib
45
+ missing in this module, he/she may apply PyPBLib as a standalone library,
46
+ when working with PySAT.
47
+
48
+ .. [1] Tobias Philipp, Peter Steinke. *PBLib - A Library for Encoding
49
+ Pseudo-Boolean Constraints into CNF*. SAT 2015. pp. 9-16
50
+
51
+ A *pseudo-Boolean constraint* is a constraint of the form:
52
+ :math:`\\left(\\sum_{i=1}^n{a_i\\cdot x_i}\\right)\\circ k`, where
53
+ :math:`a_i\\in\\mathbb{N}`, :math:`x_i\\in\\{y_i,\\neg{y_i}\\}`,
54
+ :math:`y_i\\in\\mathbb{B}`, and :math:`\\circ\\in\\{\\leq,=,\\geq\\}`.
55
+ Pseudo-Boolean constraints arise in a number of important practical
56
+ applications. Thus, several *encodings* of pseudo-Boolean constraints into
57
+ CNF formulas are known [2]_. The list of pseudo-Boolean encodings
58
+ supported by this module include BDD [3]_ [4]_, sequential weight counters
59
+ [5]_, sorting networks [3]_, adder networks [3]_, and binary merge [6]_.
60
+ Access to all cardinality encodings can be made through the main class of
61
+ this module, which is :class:`.PBEnc`.
62
+
63
+ .. [2] Olivier Roussel, Vasco M. Manquinho. *Pseudo-Boolean and
64
+ Cardinality Constraints*. Handbook of Satisfiability. 2009.
65
+ pp. 695-733
66
+
67
+ .. [3] Niklas Eén, Niklas Sörensson. *Translating Pseudo-Boolean
68
+ Constraints into SAT*. JSAT. vol. 2(1-4). 2006. pp. 1-26
69
+
70
+ .. [4] Ignasi Abío, Robert Nieuwenhuis, Albert Oliveras,
71
+ Enric Rodríguez-Carbonell. *BDDs for Pseudo-Boolean Constraints -
72
+ Revisited*. SAT. 2011. pp. 61-75
73
+
74
+ .. [5] Steffen Hölldobler, Norbert Manthey, Peter Steinke. *A Compact
75
+ Encoding of Pseudo-Boolean Constraints into SAT*. KI. 2012.
76
+ pp. 107-118
77
+
78
+ .. [6] Norbert Manthey, Tobias Philipp, Peter Steinke. *A More Compact
79
+ Translation of Pseudo-Boolean Constraints into CNF Such That
80
+ Generalized Arc Consistency Is Maintained*. KI. 2014. pp. 123-134
81
+
82
+ ==============
83
+ Module details
84
+ ==============
85
+ """
86
+
87
+ #
88
+ #==============================================================================
89
+ import math
90
+ from pysat.formula import CNFPlus
91
+
92
+ # checking whether or not pypblib is available and working as expected
93
+ pblib_present = True
94
+ try:
95
+ from pypblib import pblib
96
+ except ImportError:
97
+ pblib_present = False
98
+
99
+
100
+ #
101
+ #==============================================================================
102
+ class NoSuchEncodingError(Exception):
103
+ """
104
+ This exception is raised when creating an unknown LEQ, GEQ, or Equals
105
+ constraint encoding.
106
+ """
107
+
108
+ pass
109
+
110
+
111
+ #
112
+ #==============================================================================
113
+ class EncType(object):
114
+ """
115
+ This class represents a C-like ``enum`` type for choosing the
116
+ pseudo-Boolean encoding to use. The values denoting the encodings are:
117
+
118
+ ::
119
+
120
+ best = 0
121
+ bdd = 1
122
+ seqcounter = 2
123
+ sortnetwrk = 3
124
+ adder = 4
125
+ binmerge = 5
126
+ native = 6
127
+
128
+ The desired encoding can be selected either directly by its integer
129
+ identifier, e.g. ``2``, or by its alphabetical name, e.g.
130
+ ``EncType.seqcounter``.
131
+
132
+ All the encodings are produced and returned as a list of clauses in
133
+ the :class:`pysat.formula.CNFPlus` format.
134
+
135
+ Note that the encoding type can be set to ``best``, in which case the
136
+ encoder selects one of the other encodings from the list (in most
137
+ cases, this invokes the ``bdd`` encoder).
138
+ """
139
+
140
+ assert pblib_present, 'Package \'pypblib\' is unavailable. Check your installation.'
141
+
142
+ best = 0
143
+ bdd = 1
144
+ seqcounter = 2
145
+ sortnetwrk = 3
146
+ adder = 4
147
+ binmerge = 5
148
+ native = 6
149
+
150
+ # mapping from internal encoding identifiers to the ones of PyPBLib
151
+ _to_pbenc = {
152
+ best: pblib.PB_BEST,
153
+ bdd: pblib.PB_BDD,
154
+ seqcounter: pblib.PB_SWC,
155
+ sortnetwrk: pblib.PB_SORTINGNETWORKS,
156
+ adder: pblib.PB_ADDER,
157
+ binmerge: pblib.PB_BINARY_MERGE
158
+ }
159
+
160
+ # mapping from internal comparator identifiers to the ones of PyPBLib
161
+ _to_pbcmp = {
162
+ '<': pblib.LEQ,
163
+ '>': pblib.GEQ,
164
+ '=': pblib.BOTH
165
+ }
166
+
167
+
168
+ #
169
+ #==============================================================================
170
+ class PBEnc(object):
171
+ """
172
+ Abstract class responsible for the creation of pseudo-Boolean
173
+ constraints encoded to a CNF formula. The class has three main *class
174
+ methods* for creating LEQ, GEQ, and Equals constraints. Given (1)
175
+ either a list of weighted literals or a list of unweighted literals
176
+ followed by a list of weights, (2) an integer bound and an encoding
177
+ type, each of these methods returns an object of class
178
+ :class:`pysat.formula.CNFPlus` representing the resulting CNF formula.
179
+
180
+ Since the class is abstract, there is no need to create an object of
181
+ it. Instead, the methods should be called directly as class methods,
182
+ e.g. ``PBEnc.atmost(wlits, bound)`` or ``PBEnc.equals(lits, weights,
183
+ bound)``. An example usage is the following:
184
+
185
+ .. code-block:: python
186
+
187
+ >>> from pysat.pb import *
188
+ >>> cnf = PBEnc.atmost(lits=[1, 2, 3], weights=[1, 2, 3], bound=3)
189
+ >>> print(cnf.clauses)
190
+ [[4], [-1, -5], [-2, -5], [5, -3, -6], [6]]
191
+ >>> cnf = PBEnc.equals(lits=[1, 2, 3], weights=[1, 2, 3], bound=3, encoding=EncType.bdd)
192
+ >>> print(cnf.clauses)
193
+ [[4], [-5, -2], [-5, 2, -1], [-5, -1], [-6, 1], [-7, -2, 6], [-7, 2], [-7, 6], [-8, -3, 5], [-8, 3, 7], [-8, 5, 7], [8]]
194
+ """
195
+
196
+ @classmethod
197
+ def _update_vids(cls, cnf, inp, vpool):
198
+ """
199
+ Update variable ids in the given formula and id pool. The literals
200
+ serving as the input to the cardinality constraint are not
201
+ updated.
202
+
203
+ :param cnf: a list of literals in the sum.
204
+ :param inp: the list of input literals
205
+ :param vpool: the value of bound :math:`k`.
206
+
207
+ :type cnf: :class:`.formula.CNFPlus`
208
+ :type inp: list(int)
209
+ :type vpool: :class:`.formula.IDPool`
210
+ """
211
+
212
+ top, vmap = max(inp + [vpool.top]), {} # current top and variable mapping
213
+
214
+ # we are going to use this to check if literals are input
215
+ inp = set([abs(l) for l in inp])
216
+
217
+ # creating a new variable mapping, taking into
218
+ # account variables marked as "occupied"
219
+ while top < cnf.nv:
220
+ top += 1
221
+
222
+ # skipping the input literals
223
+ if top in inp:
224
+ vmap[top] = top
225
+ continue
226
+
227
+ vpool.top += 1
228
+
229
+ while vpool._occupied and vpool.top >= vpool._occupied[0][0]:
230
+ if vpool.top <= vpool._occupied[0][1] + 1:
231
+ vpool.top = vpool._occupied[0][1] + 1
232
+
233
+ vpool._occupied.pop(0)
234
+
235
+ # mapping this literal to a free one
236
+ vmap[top] = vpool.top
237
+
238
+ # updating the clauses
239
+ for cl in cnf.clauses:
240
+ cl[:] = map(lambda l: int(math.copysign(vmap[abs(l)], l)) if abs(l) in vmap else l, cl)
241
+
242
+ # updating the number of variables
243
+ cnf.nv = vpool.top
244
+
245
+ @classmethod
246
+ def _encode(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
247
+ encoding=EncType.best, comparator='<', conditionals=None):
248
+ """
249
+ This is the method that wraps the encoder of PyPBLib. Although the
250
+ method can be invoked directly, a user is expected to call one of
251
+ the following methods instead: :meth:`atmost`, :meth:`atleast`, or
252
+ :meth:`equals`.
253
+
254
+ The list of literals can contain either integers or pairs ``(l,
255
+ w)``, where ``l`` is an integer literal and ``w`` is an integer
256
+ weight. The latter can be done only if no ``weights`` are
257
+ specified separately.
258
+
259
+ :param lits: a list of literals in the sum.
260
+ :param weights: a list of weights
261
+ :param bound: the value of bound :math:`k`.
262
+ :param top_id: top variable identifier used so far.
263
+ :param vpool: variable pool for counting the number of variables.
264
+ :param encoding: identifier of the encoding to use.
265
+ :param comparator: identifier of the comparison operator
266
+
267
+ :type lits: iterable(int)
268
+ :type weights: iterable(int)
269
+ :type bound: int
270
+ :type top_id: integer or None
271
+ :type vpool: :class:`.IDPool`
272
+ :type encoding: integer
273
+ :type comparator: str
274
+
275
+ :rtype: :class:`pysat.formula.CNFPlus`
276
+ """
277
+
278
+ if encoding < 0 or encoding > 6:
279
+ raise(NoSuchEncodingError(encoding))
280
+
281
+ # checking if the bound is meaningless for any encoding
282
+ if bound < 0:
283
+ raise ValueError('Wrong bound: {0}'.format(bound))
284
+
285
+ assert not top_id or not vpool, \
286
+ 'Use either a top id or a pool of variables but not both.'
287
+
288
+ # we are going to return this formula
289
+ ret = CNFPlus()
290
+
291
+ # if the list of literals is empty, return empty formula
292
+ if not lits:
293
+ return ret
294
+
295
+ # preparing weighted literals
296
+ if weights:
297
+ assert len(lits) == len(weights), 'Same number of literals and weights is expected.'
298
+ wlits = [(l, w) for l, w in zip(lits, weights)]
299
+ else:
300
+ if all(map(lambda lw: (type(lw) in (list, tuple)) and len(lw) == 2, lits)):
301
+ # literals are already weighted
302
+ lits, weight = zip(*lits) # unweighted literals for getting top_id
303
+ elif all(map(lambda l: type(l) is int, lits)):
304
+ # no weights are provided => all weights are units
305
+ wlits = [(l, 1) for l in lits]
306
+ weights = [1 for l in lits]
307
+ else:
308
+ assert 0, 'Incorrect literals given.'
309
+
310
+ # obtaining the top id from the variable pool
311
+ if vpool:
312
+ top_id = vpool.top
313
+
314
+ # choosing the maximum id among the current top and the list of literals
315
+ if conditionals is None:
316
+ conditionals = []
317
+ top_id = max(map(lambda x: abs(x), conditionals + lits + [top_id if top_id != None else 0]))
318
+
319
+ # native representation
320
+ if encoding == 6:
321
+ ret.nv = top_id
322
+
323
+ if comparator == '<':
324
+ ret.atmosts = [(lits, bound, weights)]
325
+ elif comparator == '>':
326
+ ret.atmosts = [(list(map(lambda l: -l, lits)), sum(weights) - bound, weights)]
327
+ elif comparator: # comparator == '='
328
+ ret.atmosts = [(lits, bound, weights),
329
+ (list(map(lambda l: -l, lits)), sum(weights) - bound, weights)]
330
+
331
+ return ret
332
+
333
+ assert pblib_present, 'Package \'pypblib\' is unavailable. Check your installation.'
334
+
335
+ # pseudo-Boolean constraint and variable manager
336
+ constr = pblib.PBConstraint([pblib.WeightedLit(*wl) for wl in wlits],
337
+ EncType._to_pbcmp[comparator], bound)
338
+
339
+ varmgr = pblib.AuxVarManager(top_id + 1)
340
+
341
+ # add optional conditionals
342
+ if len(conditionals) > 0:
343
+ constr.add_conditionals(conditionals)
344
+
345
+ # encoder configuration
346
+ config = pblib.PBConfig()
347
+ config.set_PB_Encoder(EncType._to_pbenc[encoding])
348
+
349
+ # encoding
350
+ result = pblib.VectorClauseDatabase(config)
351
+ pb2cnf = pblib.Pb2cnf(config)
352
+ pb2cnf.encode(constr, result, varmgr)
353
+
354
+ # extracting clauses
355
+ ret.clauses = result.get_clauses()
356
+ ret.nv = max(ret.nv, top_id, varmgr.get_biggest_returned_auxvar()) # needed if no auxiliary variable is used
357
+
358
+ # updating vpool if necessary
359
+ if vpool:
360
+ if vpool._occupied and vpool.top <= vpool._occupied[0][0] <= ret.nv:
361
+ cls._update_vids(ret, vpool, lits)
362
+ else:
363
+ vpool.top = ret.nv - 1
364
+ vpool._next()
365
+
366
+ return ret
367
+
368
+ @classmethod
369
+ def leq(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
370
+ encoding=EncType.best, conditionals=None):
371
+ """
372
+ This method can be used for creating a CNF encoding of a LEQ
373
+ (weighted AtMostK) constraint, i.e. of
374
+ :math:`\\sum_{i=1}^{n}{a_i\\cdot x_i}\\leq k`. The resulting set
375
+ of clauses is returned as an object of class
376
+ :class:`.formula.CNF`.
377
+
378
+ The input list of literals can contain either integers or pairs
379
+ ``(l, w)``, where ``l`` is an integer literal and ``w`` is an
380
+ integer weight. The latter can be done only if no ``weights`` are
381
+ specified separately. The type of encoding to use can be specified
382
+ using the ``encoding`` parameter. By default, it is set to
383
+ ``EncType.best``, i.e. it is up to the PBLib encoder to choose the
384
+ encoding type.
385
+
386
+ The final optional argument is ``conditionals``, where a list of
387
+ literals can be passed to be used as the antecedent for the PB
388
+ constraint, which makes it *"reified"*. If the argument is set to
389
+ ``None``, the constraint won't be reified.
390
+
391
+ :param lits: a list of literals in the sum.
392
+ :param weights: a list of weights
393
+ :param bound: the value of bound :math:`k`.
394
+ :param top_id: top variable identifier used so far.
395
+ :param vpool: variable pool for counting the number of variables.
396
+ :param encoding: identifier of the encoding to use.
397
+ :param conditionals: a list of variables that imply this constraint.
398
+
399
+ :type lits: iterable(int)
400
+ :type weights: iterable(int)
401
+ :type bound: int
402
+ :type top_id: integer or None
403
+ :type vpool: :class:`.IDPool`
404
+ :type encoding: integer
405
+ :type conditionals: list(int) or None
406
+
407
+ :rtype: :class:`pysat.formula.CNFPlus`
408
+ """
409
+
410
+ return cls._encode(lits, weights=weights, bound=bound, top_id=top_id,
411
+ vpool=vpool, encoding=encoding, comparator='<',
412
+ conditionals=conditionals)
413
+
414
+ @classmethod
415
+ def atmost(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
416
+ encoding=EncType.best, conditionals=None):
417
+ """
418
+ A synonim for :meth:`PBEnc.leq`.
419
+ """
420
+
421
+ return cls.leq(lits, weights=weights, bound=bound, top_id=top_id,
422
+ vpool=vpool, encoding=encoding,
423
+ conditionals=conditionals)
424
+
425
+ @classmethod
426
+ def geq(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
427
+ encoding=EncType.best, conditionals=None):
428
+ """
429
+ This method can be used for creating a CNF encoding of a GEQ
430
+ (weighted AtLeastK) constraint, i.e. of
431
+ :math:`\\sum_{i=1}^{n}{a_i\\cdot x_i}\\geq k`. The method shares
432
+ the arguments and the return type with method :meth:`PBEnc.leq`.
433
+ Please, see it for details.
434
+ """
435
+
436
+ return cls._encode(lits, weights=weights, bound=bound, top_id=top_id,
437
+ vpool=vpool, encoding=encoding, comparator='>',
438
+ conditionals=conditionals)
439
+
440
+ @classmethod
441
+ def atleast(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
442
+ encoding=EncType.best, conditionals=None):
443
+ """
444
+ A synonym for :meth:`PBEnc.geq`.
445
+ """
446
+
447
+ return cls.geq(lits, weights=weights, bound=bound, top_id=top_id,
448
+ vpool=vpool, encoding=encoding,
449
+ conditionals=conditionals)
450
+
451
+ @classmethod
452
+ def equals(cls, lits, weights=None, bound=1, top_id=None, vpool=None,
453
+ encoding=EncType.best, conditionals=None):
454
+ """
455
+ This method can be used for creating a CNF encoding of a weighted
456
+ EqualsK constraint, i.e. of :math:`\\sum_{i=1}^{n}{a_i\\cdot x_i}=
457
+ k`. The method shares the arguments and the return type with
458
+ method :meth:`PBEnc.leq`. Please, see it for details.
459
+ """
460
+
461
+ return cls._encode(lits, weights=weights, bound=bound, top_id=top_id,
462
+ vpool=vpool, encoding=encoding, comparator='=',
463
+ conditionals=conditionals)