diff options
Diffstat (limited to 'builtins.c')
-rw-r--r-- | builtins.c | 51 |
1 files changed, 51 insertions, 0 deletions
@@ -23,6 +23,7 @@ BuiltinProto(builtincompare); BuiltinProto(builtinfunctor); BuiltinProto(builtinarg); BuiltinProto(builtinuniv); +BuiltinProto(builtinis); int compareterms(Term *, Term *); @@ -78,6 +79,8 @@ findbuiltin(Term *goal) return builtinarg; if(Match(L"=..", 2)) return builtinuniv; + if(Match(L"is", 2)) + return builtinis; return nil; } @@ -433,4 +436,52 @@ builtinuniv(Term *database, Term *goal, Goal **goals, Choicepoint **choicestack, Term *reallist = mkcompound(L".", 2, t); return unify(list, reallist, bindings); } +} + +#define ToFloat(t) (t->numbertype == NumberInt ? (double)t->ival : t->dval) + +Term * +aritheval(Term *expr) +{ + /* Not every arithmetic operation is defined right now. */ + + if(expr->tag == NumberTerm) + return expr; + else if(expr->tag == CompoundTerm && expr->arity == 2){ + Term *A = aritheval(expr->children); + Term *B = aritheval(expr->children->next); + Term *result = mknumber(NumberInt, 0, 0); + + if(A == nil || B == nil) + return nil; + if(runestrcmp(expr->text, L"+") == 0){ + if(A->numbertype == NumberInt && B->numbertype == NumberInt){ + result->numbertype = NumberInt; + result->ival = A->ival + B->ival; + }else{ + result->numbertype = NumberFloat; + result->dval = ToFloat(A) + ToFloat(B); + } + }else + return nil; + return result; + }else + return nil; +} + +int +builtinis(Term *database, Term *goal, Goal **goals, Choicepoint **choicestack, Binding **bindings) +{ + USED(database); + USED(goals); + USED(choicestack); + Term *result = goal->children; + Term *expr = result->next; + + + Term *realresult = aritheval(expr); + if(realresult) + return unify(result, realresult, bindings); + else + return 0; }
\ No newline at end of file |