[pypy-svn] r25146 - pypy/dist/pypy/doc

auc at codespeak.net auc at codespeak.net
Thu Mar 30 17:49:09 CEST 2006


Author: auc
Date: Thu Mar 30 17:49:08 2006
New Revision: 25146

Modified:
   pypy/dist/pypy/doc/constraints-and-logic.txt
Log:
update reflecting current state of affairs ...


Modified: pypy/dist/pypy/doc/constraints-and-logic.txt
==============================================================================
--- pypy/dist/pypy/doc/constraints-and-logic.txt	(original)
+++ pypy/dist/pypy/doc/constraints-and-logic.txt	Thu Mar 30 17:49:08 2006
@@ -11,38 +11,35 @@
 -----
 
 This document tries to shed some light on integration of logic and
-constraint programming into Python using the PyPy
-framework.
+constraint programming into Python using the PyPy framework.
+
+This takes place in Working Packages 09 and 10 of the EU PyPy funding
+project. The logic and constraint programming features are to be added
+to PyPy (WP9). An ontology library will be provided and will serve as
+our first use case for logic programming.
 
 PyPy has been progressively equiped with a parser and compiler
 flexible enough that it is hoped that developpers can leverage it to
 extend the language *at runtime*. This is quite in the spirit of Lisp
-macros, if not the exact manner.
-
-This takes place in Working Packages 09 and 10 of the EU PyPy funding
-project. It is expected that an aspect oriented programming toolkit be
-built using the compiler and parser infrastructure (WP10), and that the
-logic and constraint programming features be added to PyPy (WP9). An
-ontology library will be provided and will serve as our first use
-case for logic programming.
+macros, if not the exact manner. It is expected that an aspect
+oriented programming toolkit be built using the compiler and parser
+infrastructure (WP10). This will serve the needs of WP9.
 
 Clarifications
 --------------
 
 This work was described as integration of logic programming *and*
-constraint programming into PyPy. Both are obviously related but we
-don't know if they will share, in PyPy, the same syntax and the same
-machinery.
-
-Also it has been said that CLP will be inspired from what is done in
-the Oz programming language (http://www.mozart-oz.org/), which
-provides different programming 'paradigms' with a very well
-thought-out integration between said paradigms. For instance,
-imperative features can be mixed, to some extent, with logic
-programming (the later can be 'embedded' in the former); or constraint
-programming goes with stateless concurrency, another important feature
-of Oz. We still don't know to what extent the Oz level of integration
-will be pursued in the context of PyPy, esp. WP 9 and 10.
+constraint programming into PyPy. Both are obviously related and we
+have settled on the concurrent logic and constraint programing (CCLP)
+model present in the Oz programing language. It allows to write
+logic (Prolog-style) programs and to use constraint solving
+techniques in an integrated manner (as opposed to the use of an
+external toolkit with high impedance mismatch between language runtime
+and constraint solving package). The relational way will be built on
+the constraint solving machinery (much like, in Oz, the *choice*
+operator is built on top of *choose*).
+
+This will allow 
 
 Lastly, here we mainly discuss syntactical issues: those are probably
 the least difficult aspects of getting CLP into python; getting an
@@ -54,18 +51,19 @@
 
 In constraint programming, a 'problem' is a set of variables, their
 (finite discrete) domains, and the constraints that restrict their
-possible values. When all these have been given to a constraint
-solver, it is possible to find all possible solutions, that is the
-sets of valuations that satisfies simultaneously all constraints. The
-solver is solely responsible for finding solutions (or lack thereof).
+possible values (or define the relations between the values). When all
+these have been given to a constraint solver, it is possible to find
+all possible solutions, that is the sets of valuations that satisfies
+simultaneously all constraints. The solver is solely responsible for
+finding solutions (or lack thereof).
 
 Overview in python
 ------------------
 
 At the time being, there exists a *constraints* package made by
-Logilab and written in pure python, which implements the solver found
-in Mozart (the reference Oz implementation). We use it to illustrate
-where we want to go, syntactically-wise.
+Logilab and written in pure python, which implements some parts of the
+solver found in Mozart (the reference Oz implementation). We use it to
+illustrate where we want to go, syntactically-wise.
 
 Let's start with a quite standard example (the problem being solved
 here is fully described on
@@ -130,14 +128,16 @@
 
 Specifiying a constraint is clunky : variables and operator have to be
 provided separately, and the operator has to be a string. This last
-restriction because Python doesn't allow passing builtin (infix)
+restriction because Python doesn't allow passing builtin infix
 operators as functional parameters.
 
+(the following sub-chapters are considered deprecated)
+
 Special operator for CLP variable bindings
 ------------------------------------------
 
-First, promote variables from third-class to second-class
-citizenry. Be able to write something like::
+First, promote variables to second-class citizenry. Be able to write
+something like::
 
  domain = [(room,slot) 
            for room in ('room A','room B','room C') 
@@ -214,142 +214,218 @@
 other hand, the lexically bounded mini-language proposed above helps
 solve this more uniformly.
 
-Logic Programming, Prolog-style
-===============================
-
-Good old logic programming has an already long syntactic tradition; we
-should probably not try to evade it too much. Thus we propose again a
-mini-language embedding horn-clauses and logic stuff into 'normal'
-(unsuspecting) Python programs.
-
-Existing python/prolog projects can be found at :
-http://christophe.delord.free.fr/en/pylog/ and
-http://aima.cs.berkeley.edu/python/logic.html. There might be more of
-them.
-
-
-Databases and Requests
-----------------------
-
-Databases contain facts, rules and requests::
-
- >>> database Numbers: # we def a logic db and enter prolog space
- ...    natural(z)
- ...    natural(s(X)) if natural(X)
- ...    r1: natural(s(s(s(z)))) # kind of named request
- ...
- >>> Numbers 
- <LogicDB object at ...>
- >>> Numbers = 42 
- NotAssignable exception, etc.
-
-
-Integration in Python
----------------------
-
-::
-
- # databases as first class objects
- get_logic_databases() # -> [Numbers]
-
- # return values in Python space
- d1 = get_logic_databases()[0]
- d1.ask('r1') -> True
+Logic Programming, Prolog and Oz-style
+======================================
 
- # extending an existing database
- database Numbers: # adds up to existing Numbers db (eyebrows raise)
-     pair(z)
-     pair(s(s(X))) if pair(X)
+Integrated search seamlessly into an already grown up imperative
+programming language might cause some headaches. For instance, in the
+perspective of benefiting from the Prolog way of doing logic
+programming, we considered embedding a specific mini-language into
+Python with strong and well-defined borders between the logic world
+and the 'normal', or usual imperative world of standard Python.
+
+Such a twist might be not needed, fortunately. Designers of Oz have
+devised another way of doing logic programming that is certainly much
+more easily integrable into current Python than bolting Prolog into
+it.
+
+Criticism of Prolog
+-------------------
+
+The Prolog-style for logic programming, while successfully applied to
+many real-world problems, is not without defects. These can be
+summarized as the following :
+
+* Prolog is a compromise between relational and algorithmic style of
+  programming. It does not go far enough on the side of
+  relations/constraints (horn clauses have limited expressiveness) and
+  makes unnatural to write algorithmic (non-searching) code.
+
+* it is completely unsuitable to concurrent programming, which is
+  becoming more regarded as new languages allow to do it with
+  high-level, hassle-free constructs, and is a necessity to build
+  reactive applications.
+
+
+Integration in PyPy
+-------------------
+
+From the PyPy sprint in Belgium that was focused on constraint and
+logic programming emerged an implementation of a so-called 'Logic
+Objectspace' which extends PyPy's standard object space implementing
+standard Python operations with two things :
+
+* micro threads (which despite their names are merely, currently,
+  greenlets, that is a kind of coroutine)
+
+* Logic Variables, that is a new datatype acting as a box for normal
+  Python values. 
+
+
+Logic Variables
+---------------
+
+Logic variables have two states : free and bound. A bound logic
+variable is indistinguishable from a normal Python value which it
+wraps. A free variable can only be bound once (it is also said to be a
+single-assignment variable). 
+
+The operation that binds a logic variable is known as
+"unification". Unify is an operator that takes two arbitrary data
+structures and tries to check if they are the same, much in the sense
+of the == operator, but with one twist : unify is a "destructive"
+operator when it comes to logic variables.
+
+Unifying one unbound variable with some value means assigning the
+value to the variable (which then satisfies equalness), unifying two
+unbound variables aliases them (they are constrained to reference the
+same -future- value). Thus unify can change the state of the world and
+raises an UnificationError exception whenever it fails, instead of
+returning False like an equality predicate.
+
+Assignment or aliasing of variables is provided by the 'bind' operator.
+
+Threads and dataflow synchronisation
+------------------------------------
+
+When a piece of code tries to access a free logic variable, the thread
+in which it runs is blocked (suspended) until the variable becomes
+bound. This behaviour is known as "dataflow synchronization" and
+mimics exactly the dataflow variables from Oz. With respect to
+behaviour under concurrency conditions, logic variables come with two
+operators :
+
+* wait : this suspends the current thread until the variable is bound,
+  it returns the value otherwise (in the logic objectspace, all
+  operators make an implicit, transparent wait on their value arguments)
+
+* wait_needed : this suspends the current thread until the variable
+  has received a wait message. It has to be used explicitely,
+  typically by a producer thread that wants to produce data only when
+  needed.
+
+* bind : binding a variable to a value will make runnable all threads
+  suspended this variable.
+
+Wait and wait_needed allow to write efficient lazy evaluating code.
+
+Relation with logic programming
+-------------------------------
+
+All of this is not sufficient without a specific non-deterministic
+primitive operator added to the language. In Oz, the 'choice' operator
+allows to statically enumerate a set of possible actions, leaving the
+actual decision to choose between several branches to the solver.
+
+Let us look at a small relational program written respectively in
+Prolog, Oz and extended Python.
+
+Prolog :
+
+ Soft(beige).
+ Soft(coral).
+ Hard(mauve).
+ Hard(ochre).
+
+ Contrast(C1, C2) :- Soft(C1), Hard(C2).
+ Contrast(C1, C2) :- Hard(C1), Soft(C2).
+
+ Suit(Shirt, Pants, Socks) :- Contrast(Shirt, Pants), 
+   Contrast(Pants, Socks), Shirt != Socks.
+
+Oz :
+
+ fun {Soft} choice beige [] coral end end
+ fun {Hard} choice mauve [] ochre end end
+
+ proc {Contrast C1 C2}
+     choice C1={Soft} C2={Hard}[] C1={Hard} C2={Soft} end
+ end
+
+ fun {Suit}
+     Shirt Pants Socks
+ in
+     {Contrast Shirt Pants}
+     {Contrast Pants Socks}
+     if Shirt==Socks then fail end
+     suit(Shirt Pants Socks)
+ end
+
+Python :
+
+ def soft():
+     choice: 'beige' or: 'coral'
+
+ def hard():
+     choice: 'mauve' or: 'ochre'
+
+ def contrast(C1, C2):
+     choice:
+        unify(C1, soft())
+        unify(C2, hard())
+     or:
+        unify(C1, hard())
+        unify(C2, soft())
+
+ def suit():
+     let Shirt, Pants, Socks:
+         contrast(Shirt, Pants)
+         contrast(Pants, Socks)
+         if Shirt == Socks: raise UnificationError
+         return (Shirt, Pants, Socks)
+
+Since our variables (those created by the let declaration) really are
+logic variables, and thus can be assigned to only once, the solver
+must take some special measure to get all the solutions. The trick is
+that the solver uses the Computation Space machinery for constraint
+solving. Basically, a computation space is like an independant world
+in which a specific, unique combination of choices will be tried and
+eventually a -locally- unique solution be produced. The solver uses as
+many computation spaces as neccessary to eventually enumerate all
+possible solutions.
 
- # database acquisition (inheritance ?)
- database Ratios(Numbers):
-     pass
 
- # adding rules and requests from Python space
- d2 = get_logic_databases[1] # the Ratios db
- d2.add_rule('ratio(X,Y) if Y != z, natural(X), natural(Y)')
- 
- d2.add_request('r2', 'ratio(s(z),toto)')
- d2.ask('r2') -> False
+Done and To Do
+==============
 
+What has been done
+------------------
 
-Thus, the logic and Python stuff are cleanly separated, and of course
-we forbid lexical capture as in::
-
- z = 42
- database Numbers:
-     natural(z)
-
-A (maybe) nicer way to ask could be::
-
- database Family :
-
-     father(jean, pierre)
-     father(paul, jean)
-     grandfather(X,Y) if father(X,Z) and father(Z,Y)
-    
- Family.grandfather(jean, A)
-
-
-Conclusion
-----------
-
-Syntax is not all-important but can touch on the nerves of some. It
-sometimes involves relogious arguments. We hope to irritate none with
-this proposal; we merely expect counter-proposals or more detailed
-proposals or agreement or just indiference on this.
+For constraint programming:
 
+* A prototype concurrent solver using Computation Spaces, CPython
+  threads and the existing logilab constraints package has been built
+  and shown to work (note that it is not 100% complete in the sense
+  that the part that allows logic programming to be used is not
+  there. Only recently has this been figured out).
 
-CLP and Oz
-==========
+* A simulation of dataflow/logic variables has been built.
 
-The Oz programming language is and will be a driving inspiration for
-all deep integration work of CLP. Logilab constraints pure python
-package already implements search according to Oz (without the
-concurrency parts).
+For logic programming:
 
-(don't forget to have a serious look at Screamer/CL)
+* A prototype logic object space has been built, which provides
+  integrated logic variables with dataflow semantics, an incomplete
+  implementation of micro threads, 
 
-What shall be done 
-------------------
+What needs to be done 
+---------------------
 
 For constraint programming:
 
-* Adapt the core algorithms from logilab.constraints to RPython
-* Stuff it into PyPy
-* Enhance (tm) it with concurrency aspects (needs preemptive
-  threading)
+* Reimplement the computation space as an entity of the logic object
+  space (we think that reusing thread pickling abilities would be an
+  interesting start).
+
+* Adapt the core algorithms to RPython
 
 Logic programming:
 
-* Investigate how much of above can be reused
-* Pick a strategy (reuse constraints or implement unification)
-* Implement deep into PyPy
+* Provide a basic solver (depth-first), and a working choose() space
+  operator to allow search as provided in logic programming.
 
 For both:
 
-* Adapt the parser/lexer to the syntactic requirements
-
-
-Ideas of testbeds
-=================
-
-try to use logic related features in all of these python projects to
-make sure of the design and implementation of logic in pypy.
-
-- rdflib.sparql an implementation of W3C's SPARQL language coupled
-  with redfoot.
-  http://rdflib.net/2005/09/10/rdflib-2.2.2/html/public/rdflib.sparql-module.html
-
-- cwm a rule-based engine for rdf inferencing
-  http://www.w3.org/2000/10/swap/doc/cwm.html
-
-- pychinko an implementation of RETE algorithm for rule-based systems
-  http://www.mindswap.org/~katz/pychinko/
-  http://en.wikipedia.org/wiki/Rete_algorithm
+* Adapt the parser/lexer to the syntactic requirements (which should
+  be light).
 
-- pylint: using constraints to generate design-related comments and
-  warnings is done in SOUL or doable with pyontology
-  http://www.logilab.org/projects/pylint
 
-- pyontology. DFKI's OWL manipulation tool (see svn)



More information about the Pypy-commit mailing list