[pypy-svn] r45102 - in pypy/dist/pypy/lang/scheme: . test

mwh at codespeak.net mwh at codespeak.net
Sun Jul 15 13:44:38 CEST 2007


Author: mwh
Date: Sun Jul 15 13:44:38 2007
New Revision: 45102

Modified:
   pypy/dist/pypy/lang/scheme/object.py
   pypy/dist/pypy/lang/scheme/test/test_eval.py
   pypy/dist/pypy/lang/scheme/test/test_object.py
Log:
support for the (define (<name> <formals>) <body>) sugar
feel free to revert if this is wrong/broken/in an inappropriate style/in the
way in any way


Modified: pypy/dist/pypy/lang/scheme/object.py
==============================================================================
--- pypy/dist/pypy/lang/scheme/object.py	(original)
+++ pypy/dist/pypy/lang/scheme/object.py	Sun Jul 15 13:44:38 2007
@@ -527,13 +527,25 @@
     def call(self, ctx, lst):
         if not isinstance(lst, W_Pair):
             raise SchemeSyntaxError
-        w_identifier = lst.car
-        if not isinstance(w_identifier, W_Identifier):
-            raise WrongArgType(w_identifier, "Identifier")
+        w_first = lst.car
+        if isinstance(w_first, W_Identifier):
+            w_val = lst.get_cdr_as_pair().car.eval(ctx)
+            ctx.set(w_first.name, w_val)
+            return w_val
+        elif isinstance(w_first, W_Pair):
+            return self.call(ctx, self._convert_lambda(lst))
+        else:
+            raise WrongArgType(w_first, "Identifier")
+    def _convert_lambda(self, lst):
+        # turn (define (<name> . <formals>) <body>) into
+        # (define <name> (lambda <formals> <body>))
+        # a more declarative version of this would be good...
+        return W_Pair(lst.car.car,
+                      W_Pair(W_Pair(Lambda(self.pname),
+                                    W_Pair(lst.car.cdr,
+                                           lst.cdr)),
+                             W_Nil()))
 
-        w_val = lst.get_cdr_as_pair().car.eval(ctx)
-        ctx.set(w_identifier.name, w_val)
-        return w_val
 
 class Sete(W_Macro):
     def call(self, ctx, lst):

Modified: pypy/dist/pypy/lang/scheme/test/test_eval.py
==============================================================================
--- pypy/dist/pypy/lang/scheme/test/test_eval.py	(original)
+++ pypy/dist/pypy/lang/scheme/test/test_eval.py	Sun Jul 15 13:44:38 2007
@@ -295,6 +295,13 @@
     assert w_result.cdr.car.to_number() == 6
     assert isinstance(w_result.cdr.cdr, W_Nil)
 
+def test_define_lambda_sugar():
+    ctx = ExecutionContext()
+    eval_expr(ctx, """(define (f x) (+ x 1))""")
+    w_result = eval_expr(ctx, "(f 1)")
+    assert isinstance(w_result, W_Integer)
+    assert w_result.to_number() == 2
+
 def test_quote():
     w_fnum = eval_noctx("(quote 42)")
     assert isinstance(w_fnum, W_Integer)

Modified: pypy/dist/pypy/lang/scheme/test/test_object.py
==============================================================================
--- pypy/dist/pypy/lang/scheme/test/test_object.py	(original)
+++ pypy/dist/pypy/lang/scheme/test/test_object.py	Sun Jul 15 13:44:38 2007
@@ -89,3 +89,20 @@
     ctx2.put("v1", w_fnum3)
     assert w_fnum3 is ctx2.get("v1")
 
+def test_define_sugar():
+    # this is one of those tests that looks very much like the
+    # implementation of the thing it is testing :/
+    ctx = ExecutionContext({})
+    define = Define("define")
+    identifier = W_Identifier("f")
+    formals = W_Pair(W_Identifier("x"), W_Nil())
+    body = W_Pair(W_Identifier("+"),
+                        W_Pair(W_Identifier("x"),
+                               W_Pair(W_Integer(1),
+                                      W_Nil())))
+    lst = W_Pair(W_Pair(identifier, formals), body)
+    converted = define._convert_lambda(lst)
+    assert converted.car == identifier
+    assert isinstance(converted.cdr.car.car, Lambda)
+    assert converted.cdr.car.cdr.car == formals
+    assert converted.cdr.car.cdr.cdr == body



More information about the Pypy-commit mailing list