[pypy-svn] r23590 - pypy/dist/pypy/lib/logic/computation_space

auc at codespeak.net auc at codespeak.net
Wed Feb 22 11:35:23 CET 2006


Author: auc
Date: Wed Feb 22 11:35:19 2006
New Revision: 23590

Modified:
   pypy/dist/pypy/lib/logic/computation_space/computationspace.py
   pypy/dist/pypy/lib/logic/computation_space/constraint.py
   pypy/dist/pypy/lib/logic/computation_space/problems.py
   pypy/dist/pypy/lib/logic/computation_space/state.py
   pypy/dist/pypy/lib/logic/computation_space/test_computationspace.py
   pypy/dist/pypy/lib/logic/computation_space/variable.py
Log:
no domain refactoring
misc fixes


Modified: pypy/dist/pypy/lib/logic/computation_space/computationspace.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/computationspace.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/computationspace.py	Wed Feb 22 11:35:19 2006
@@ -8,16 +8,12 @@
 
 from state import Succeeded, Distributable, Failed, Unknown
 
-from variable import EqSet, Var, NoValue, Pair, \
+from variable import EqSet, Var, NoValue, NoDom, \
      VariableException, NotAVariable, AlreadyInStore
 from constraint import FiniteDomain, ConsistencyFailure, \
      Expression
 from distributor import DefaultDistributor
 
-#FIXME: provide a NoDom token which has nothing
-#       to do with FiniteDomains
-EmptyDom = FiniteDomain([])
-
 class Alternatives(object):
 
     def __init__(self, nb_alternatives):
@@ -81,10 +77,10 @@
         self.status = None
         self.status_condition = Condition()
         self.distributor = DefaultDistributor(self)
-        self.TOP = False
+        self.parent = parent
+        self.children = set()
         
         if parent is None:
-            self.TOP = True
             self.vars = set()
             # mapping of names to vars (all of them)
             self.names = {}
@@ -95,7 +91,6 @@
             # set of all constraints 
             self.constraints = set()
             self.root = self.var('__root__')
-            self.set_dom(self.root, EmptyDom)
             # set up the problem
             self.bind(self.root, problem(self))
             # check satisfiability of the space
@@ -105,8 +100,8 @@
             self.names = parent.names
             # we should really copy stuff
             self.var_const_map = parent.var_const_map
-            self.doms = {} # shall be copied by clone
             self.constraints = parent.constraints
+            self.doms = {} # shall be copied by clone
             self.root = parent.root
             self.distributor = parent.distributor.__class__(self)
             self._init_choose_commit()
@@ -125,13 +120,11 @@
     def _make_choice_var(self):
         ComputationSpace._nb_choices += 1
         ch_var = self.var('__choice__'+str(self._nb_choices))
-        self.set_dom(ch_var, EmptyDom)
         return ch_var
 
     def _make_stable_var(self):
         ComputationSpace._nb_choices += 1
         st_var = self.var('__stable__'+str(self._nb_choices))
-        self.set_dom(st_var, EmptyDom)
         return st_var
 
     def _process(self):
@@ -156,7 +149,7 @@
         if self.status not in (Failed, Succeeded):
             self.status = Unknown
             # sync. barrier with distributor (?)
-            print "distributable vars :"
+            print "distributable vars :", self.root.val
             for var in self.root.val:
                 print "   ", var, " -> ", self.doms[var]
                 if self.dom(var).size() > 1 :
@@ -168,6 +161,9 @@
         # A space can have at most one choice point; attempting to
         # create another gives an error."
 
+    def top_level(self):
+        return self.parent is None
+
     def ask(self):
         #print "SPACE Ask() checks stability ..."
         self.STABLE.get() # that's real stability
@@ -179,14 +175,15 @@
         # should be unreachable
         print "DOMS", [(var, self.doms[var]) 
                        for var in self.vars
-                       if self.dom(var) != EmptyDom]
+                       if self.dom(var) != NoDom]
         raise NotImplementedError
 
     def clone(self):
         #XXX: lazy copy of domains would be nice
         spc = ComputationSpace(NoProblem, parent=self)
         for var in spc.vars:
-            spc.set_dom(var, self.dom(var).copy())
+            if self.dom(var) != NoDom:
+                spc.set_dom(var, self.dom(var).copy())
         spc.status = Distributable
         return spc
 
@@ -280,8 +277,8 @@
             return self.doms[var]
         except KeyError:
             print "warning : setting no domain for", var
-            self.doms[var] = EmptyDom
-            return EmptyDom
+            self.doms[var] = NoDom
+            return NoDom
 
     def get_var_by_name(self, name):
         """looks up one variable"""
@@ -300,13 +297,13 @@
 
     def is_bound(self, var):
         """check wether a var is locally bound"""
-        if self.TOP:
+        if self.top_level():
             return var.is_bound()
         return len(self.dom(var)) == 1
 
     def val(self, var):
         """return the local binding without blocking"""
-        if self.TOP: # the real thing
+        if self.top_level(): # the real thing
             return var.val
         if self.is_bound(var): # the speculative val
             return self.dom(var)[0]
@@ -333,7 +330,7 @@
     def get_variables_with_a_domain(self):
         varset = set()
         for var in self.vars:
-            if self.dom(var) != EmptyDom: varset.add(var)
+            if self.dom(var) != NoDom: varset.add(var)
         return varset
 
     def satisfiable(self, constraint):
@@ -403,7 +400,8 @@
     def satisfy_all(self):
         """really PROPAGATE"""
       
-        print "propagating on %s" % fif(self.TOP, 'top', 'child')
+        print "propagating on %s" % fif(self.top_level(),
+                                        'top', 'child')
         const_q = [(const.estimateCost(), const)
                    for const in self.constraints]
         affected_constraints = set()
@@ -449,10 +447,10 @@
         """check that the domain of var is compatible
            with the domains of the vars in the eqs
         """
-        if self.dom(var) == EmptyDom: return True
+        if self.dom(var) == NoDom: return True
         empty = set()
         for v in eqs:
-            if self.dom(v) == EmptyDom: continue
+            if self.dom(v) == NoDom: continue
             if self.dom(v).intersection(self.dom(var)) == empty:
                 return False
         return True
@@ -465,7 +463,7 @@
         """
         dom = {}
         for var in varset:
-            if self.dom(var) != EmptyDom:
+            if self.dom(var) != NoDom:
                 dom[var] = self.dom(var).copy()
         return dom
 
@@ -517,7 +515,7 @@
         # print "variable - value binding : %s %s" % (eqs, val)
         # bind all vars in the eqset to val
         for var in eqs:
-            if self.dom(var) != EmptyDom:
+            if self.dom(var) != NoDom:
                 if val not in self.dom(var).get_values():
                     # undo the half-done binding
                     for v in eqs:
@@ -614,10 +612,11 @@
 #-- quite costly & could be merged back in unify
 
 def _iterable(thing):
-    return type(thing) in [list, set]
+    return type(thing) in [tuple, frozenset]
 
 def _mapping(thing):
-    return type(thing) is dict
+    # should be frozendict (python 2.5 ?)
+    return isinstance(thing, dict)
 
 # memoizer for _unifiable
 _unifiable_memo = set()

Modified: pypy/dist/pypy/lib/logic/computation_space/constraint.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/constraint.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/constraint.py	Wed Feb 22 11:35:19 2006
@@ -1,6 +1,4 @@
-# a) new requirement : be able to postpone asking fo the
-# values of the domain
-
+from variable import NoDom
 import operator
 
 #-- Exceptions ---------------------------------------
@@ -108,7 +106,7 @@
         return '<FiniteDomain %s>' % str(self.get_values())
 
     def __eq__(self, other):
-        if other is None: return False
+        if other is NoDom: return False
         return self._values == other._values
 
     def __ne__(self, other):
@@ -121,8 +119,6 @@
 
 #-- Constraints ------------------------------------------
 
-EmptyDom = FiniteDomain([])
-
 class AbstractConstraint(object):
     
     def __init__(self, c_space, variables):
@@ -130,7 +126,7 @@
         self.cs = c_space
         self._names_to_vars = {}
         for var in variables:
-            if self.cs.dom(var) == EmptyDom:
+            if self.cs.dom(var) == NoDom:
                 raise DomainlessVariables
             self._names_to_vars[var.name] = var
         self._variables = variables

Modified: pypy/dist/pypy/lib/logic/computation_space/problems.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/problems.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/problems.py	Wed Feb 22 11:35:19 2006
@@ -5,7 +5,7 @@
 def dummy_problem(computation_space):
     ret = computation_space.var('__dummy__')
     computation_space.set_dom(ret, c.FiniteDomain([]))
-    return (ret)
+    return (ret,)
 
 def satisfiable_problem(computation_space):
     cs = computation_space

Modified: pypy/dist/pypy/lib/logic/computation_space/state.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/state.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/state.py	Wed Feb 22 11:35:19 2006
@@ -5,11 +5,10 @@
     """
     pass
 
-class Distributable:
-    pass
+class Distributable: pass
+
+class Failed(Exception): pass
+
+class Unknown: pass
 
-class Failed(Exception):
-    pass
 
-class Unknown:
-    pass

Modified: pypy/dist/pypy/lib/logic/computation_space/test_computationspace.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/test_computationspace.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/test_computationspace.py	Wed Feb 22 11:35:19 2006
@@ -550,7 +550,7 @@
         spc = newspace(problems.satisfiable_problem)
         x, y, z = spc.find_vars('x', 'y', 'z')
         print spc.doms
-        assert spc.TOP
+        assert spc.top_level()
         assert spc.dom(x) == c.FiniteDomain([-4, -2, -1, 0,
                                              1, 2, 4])
         assert spc.dom(y) == c.FiniteDomain([0, 2, 3,
@@ -567,7 +567,7 @@
         nspc = spc.clone()
         nspc.inject(more_constraints)
         x, y, z = nspc.find_vars('x', 'y', 'z')
-        assert not nspc.TOP
+        assert not nspc.top_level()
 ##         assert nspc.dom(x) == c.FiniteDomain([7])
 ##         assert nspc.dom(y) == c.FiniteDomain([6])
 ##         assert nspc.dom(z) == c.FiniteDomain([1])
@@ -595,13 +595,8 @@
                         ('room A', 'day 1 PM')]
 
 
-        
-##     def test_send_more_money_dfs(self):
-##         # we need a linear constraint solver
-##         # for this one
-##         sol = strategies.dfs_one_solution(problems.send_more_money)
-
-##         print sol
-##         assert 0
+    def test_scheduling_problem_dfs_all_solutions(self):
+        sols = strategies.dfs_all_solutions(problems.conference_scheduling)
+        assert len(sols) == 64
 
         

Modified: pypy/dist/pypy/lib/logic/computation_space/variable.py
==============================================================================
--- pypy/dist/pypy/lib/logic/computation_space/variable.py	(original)
+++ pypy/dist/pypy/lib/logic/computation_space/variable.py	Wed Feb 22 11:35:19 2006
@@ -1,8 +1,5 @@
 import threading
 
-from constraint import FiniteDomain
-
-
 #----------- Exceptions ---------------------------------
 class VariableException(Exception):
     def __init__(self, name):
@@ -17,17 +14,11 @@
         return "%s is not a variable" % self.name
 
 #----------- Variables ----------------------------------
-class EqSet(set):
-    """An equivalence set for variables"""
+class EqSet(set): pass
 
-##     def __str__(self):
-##         if len(self) == 0:
-##             return ''
-##         for var in self:
-##             '='.join(var.name)
+class NoValue: pass
 
-class NoValue:
-    pass
+class NoDom: pass
 
 class Var(object):
     """Single-assignment variable"""
@@ -115,5 +106,4 @@
         finally:
             self._value_condition.release()
 
-
-
+    



More information about the Pypy-commit mailing list