change printing
[lambda.git] / lambda.y
index 07c6b80..9155a8a 100644 (file)
--- a/lambda.y
+++ b/lambda.y
@@ -39,18 +39,35 @@ struct lambda *make_ident(char *i)
        struct lambda *r = make_lambda();
        r->which = lambda_ident;
        r->data.identifier.ident = strdup(i);
-       r->data.identifier.revision = 0;
+       r->data.identifier.binding = NULL;
        return r;
 }
 
+void lambda_bind(struct lambda *tob, struct lambda *binding, char *ident)
+{
+       switch(tob->which){
+       case lambda_ident:
+               if(strcmp(ident, tob->data.identifier.ident) == 0 && tob->data.identifier.binding == NULL)
+                       tob->data.identifier.binding = binding;
+               break;
+       case lambda_abs:
+               lambda_bind(tob->data.abstraction.expr, binding, ident);
+               break;
+       case lambda_app:
+               lambda_bind(tob->data.application.expr1, binding, ident);
+               lambda_bind(tob->data.application.expr2, binding, ident);
+               break;
+       }
+}
+
 struct lambda *make_abstraction(char *i, bool strict, struct lambda *t)
 {
        struct lambda *r = make_lambda();
        r->which = lambda_abs;
        r->data.abstraction.ident = strdup(i);
-       r->data.abstraction.revision = 0;
        r->data.abstraction.strict = strict;
        r->data.abstraction.expr = t;
+       lambda_bind(t, r, i);
        return r;
 }
 
@@ -73,9 +90,8 @@ struct lambda *make_numeral(unsigned int i)
 
 struct lambda *make_bool(bool b)
 {
-       return b
-               ? make_abstraction("a", false, make_abstraction("b", false, make_ident("a")))
-               : make_abstraction("a", false, make_abstraction("b", false, make_ident("b")));
+       return make_abstraction("a", false,
+               make_abstraction("b", false, make_ident(b ? "a" : "b")));
 }
 
 void decls_prepend(char *ident, struct lambda *value)
@@ -89,12 +105,9 @@ void decls_prepend(char *ident, struct lambda *value)
 
 struct lambda *decls_lookup(char *ident)
 {
-       struct decllist *c = decls;
-       while(c != NULL){
+       for(struct decllist *c = decls; c != NULL; c = c->next)
                if(strcmp(c->ident, ident) == 0)
                        return copy(c->value);
-               c = c->next;
-       }
        return make_ident(ident);
 }
 
@@ -115,21 +128,23 @@ program
        :
        | lambda SEMICOLON program
 lambda
-       : term
-               {
-                       int maxdepth = 1000;
-                       printf("     ");
-                       lambda_reduce($1, $1, &maxdepth);
-                       lambda_print($1, NULL);
-                       lambda_free($1);
-               }
-       | FUNC func
+       : FUNC func
                {
                        decls_prepend($1->data.identifier.ident, $2);
                        printf("%s = ", $1->data.identifier.ident);
                        lambda_print($2, NULL);
                        lambda_free($1);
                }
+       | term
+               {
+                       struct lambda *t = $1;
+                       printf("     ");
+                       for(unsigned int i = 0; i<999; i++)
+                               if(!lambda_reduce(&t, &t, false))
+                                       break;
+                       lambda_print(t, NULL);
+                       lambda_free(t);
+               }
 func
        : ASSIGN term
                { $$ = $2; }