func lambda(s *scheme.Scope, ss []scheme.Sexpr) (scheme.Sexpr, error) { if len(ss) < 2 { return nil, scheme.ProcError("lambda at least 2 arguments") } exprs := ss[1:] evalScopeParent := scheme.NewScope(s) lArgs := ss[0] f := func(callScope *scheme.Scope, ss []scheme.Sexpr) (scheme.Sexpr, error) { args := lArgs evalScope := scheme.NewScope(evalScopeParent) aC, ok := args.(*scheme.Cons) for args != scheme.Nil { if len(ss) == 0 { return nil, scheme.ProcError("invalid number of arguments") } if !ok { val := scheme.Unflatten(ss) s, k := args.(*scheme.Symbol) if !k { return nil, scheme.ProcError("Invalid parameter specification") } evalScope.Define(s, val) goto done } arg := aC.Car val := ss[0] s, k := arg.(*scheme.Symbol) if !k { return nil, scheme.ProcError("invalid parameter specification") } evalScope.Define(s, val) ss = ss[1:] args = aC.Cdr aC, ok = args.(*scheme.Cons) } if len(ss) > 0 { return nil, scheme.ProcError("Invalid number of arguments") } done: for _, e := range exprs[0 : len(exprs)-1] { eval.Eval(evalScope, e) } return eval.Eval(evalScope, exprs[len(exprs)-1]) } return scheme.CreateFunction(f, "lamba"), nil }
func addFunction(d map[*scheme.Symbol]scheme.Sexpr, name string, p scheme.Proc) { d[scheme.SymbolFromString(name)] = scheme.CreateFunction(p, name) }