add arithmetic operators
This commit is contained in:
parent
701bf84d66
commit
a740c9af25
1
README.md
Normal file
1
README.md
Normal file
@ -0,0 +1 @@
|
||||
(define fac (lambda (n) (if ((eq n 0) 1) (1 (* n (fac (+ n -1)))))))
|
||||
9
bltin.c
9
bltin.c
@ -4,6 +4,9 @@
|
||||
Object Nil = (Object){.type=OSYMBOL, .sym="nil"};
|
||||
Object Minus= (Object){.type=OBLTIN, .sym="-"};
|
||||
Object Plus = (Object){.type=OBLTIN, .sym="+"};
|
||||
Object Mul = (Object){.type=OBLTIN, .sym="*"};
|
||||
Object Div = (Object){.type=OBLTIN, .sym="/"};
|
||||
Object Mod = (Object){.type=OBLTIN, .sym="%"};
|
||||
Object Lambda= (Object){.type=OBLTIN, .sym="lambda"};
|
||||
Object Car = (Object){.type=OBLTIN, .sym="car"};
|
||||
Object Cdr = (Object){.type=OBLTIN, .sym="cdr"};
|
||||
@ -15,6 +18,9 @@ Object Eq = (Object){.type=OBLTIN, .sym="eq"};
|
||||
Object If = (Object){.type=OBLTIN, .sym="if"};
|
||||
|
||||
extern Object* fnplus(Object *, Object *);
|
||||
extern Object* fnmul(Object *, Object *);
|
||||
extern Object* fndiv(Object *, Object *);
|
||||
extern Object* fnmod(Object *, Object *);
|
||||
extern Object* fnlambda(Object *, Object *);
|
||||
extern Object* fndefine(Object *, Object *);
|
||||
extern Object* fnsetq(Object *, Object *);
|
||||
@ -37,6 +43,9 @@ bltinlookup(Object *obj)
|
||||
}bltins[] = {
|
||||
{&Lambda , fnlambda},
|
||||
{&Plus , fnplus},
|
||||
{&Mul , fnmul},
|
||||
{&Mod , fnmod},
|
||||
{&Div , fndiv},
|
||||
{&Define ,fndefine},
|
||||
{&Setq ,fnsetq},
|
||||
{&Quote ,fnquote},
|
||||
|
||||
3
dat.h
3
dat.h
@ -84,6 +84,9 @@ extern GC *gc;
|
||||
extern Object Nil;
|
||||
extern Object Minus;
|
||||
extern Object Plus;
|
||||
extern Object Mul;
|
||||
extern Object Div;
|
||||
extern Object Mod;
|
||||
extern Object Lambda;
|
||||
extern Object Car;
|
||||
extern Object Cdr;
|
||||
|
||||
49
eval.c
49
eval.c
@ -160,6 +160,55 @@ fnplus(Object *env, Object *list)
|
||||
}
|
||||
}
|
||||
|
||||
Object*
|
||||
fnmul(Object *env, Object *list)
|
||||
{
|
||||
Object *p=evallist(env, list);
|
||||
if(p->car->type != OINT)
|
||||
error("* take only [INT]");
|
||||
long sum = p->car->num;
|
||||
for(p=p->cdr;p!=&Nil; p=p->cdr){
|
||||
if(p->car->type != OINT)
|
||||
error("* take only [INT]");
|
||||
sum *= p->car->num;
|
||||
}
|
||||
return newint(gc, sum);
|
||||
}
|
||||
|
||||
Object*
|
||||
fndiv(Object *env, Object *list)
|
||||
{
|
||||
Object *p=evallist(env, list);
|
||||
if(p->car->type != OINT)
|
||||
error("/ take only [INT]");
|
||||
long sum = p->car->num;
|
||||
for(p=p->cdr;p!=&Nil; p=p->cdr){
|
||||
if(p->car->type != OINT)
|
||||
error("/ take only [INT]");
|
||||
if(p->car->num == 0)
|
||||
error("Can't div zero");
|
||||
sum /= p->car->num;
|
||||
}
|
||||
return newint(gc, sum);
|
||||
}
|
||||
|
||||
Object*
|
||||
fnmod(Object *env, Object *list)
|
||||
{
|
||||
Object *p=evallist(env, list);
|
||||
if(p->car->type != OINT)
|
||||
error("%% take only [INT]");
|
||||
long sum = p->car->num;
|
||||
for(p=p->cdr;p!=&Nil; p=p->cdr){
|
||||
if(p->car->type != OINT)
|
||||
error("%% take only [INT]");
|
||||
if(p->car->num == 0)
|
||||
error("Can't mod zero");
|
||||
sum %= p->car->num;
|
||||
}
|
||||
return newint(gc, sum);
|
||||
}
|
||||
|
||||
long
|
||||
eq(Object *env, Object *a, Object *b)
|
||||
{
|
||||
|
||||
4
obj.c
4
obj.c
@ -51,8 +51,8 @@ Object*
|
||||
newsymbol(GC *gc, char *str, int len)
|
||||
{
|
||||
static Object *syms[] = {
|
||||
&Nil, &Minus, &Plus, &Lambda, &Car, &Cdr, &Quote, &Cons,
|
||||
&Define, &Setq, &Eq, &If,
|
||||
&Nil, &Minus, &Plus, &Mul, &Mod, &Div,
|
||||
&Lambda, &Car, &Cdr, &Quote, &Cons, &Define, &Setq, &Eq, &If,
|
||||
};
|
||||
for(int i = 0; i < sizeof(syms)/sizeof(syms[0]); ++i){
|
||||
Object *c = syms[i];
|
||||
|
||||
Loading…
Reference in New Issue
Block a user