Пример #1
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            ScheminVector vec = (ScheminVector) args.Car();
            ScheminInteger pos = (ScheminInteger) args.Cdr().Car();
            IScheminType val = args.Cdr().Cdr().Car();

            int pos_int = (int) pos.IntegerValue();
            vec.List[pos_int] = val;
            return new ScheminList(true);
        }
Пример #2
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            ScheminBool condition = args.Car().BoolValue();
            IScheminType then = args.Cdr().Car();
            IScheminType otherwise = args.Cdr().Cdr().Car();

            if (condition.Value)
            {
                return then;
            }
            else
            {
                return otherwise;
            }
        }
Пример #3
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            IScheminType head = args.Car();
            IScheminType rest = args.Cdr().Car();

            if ((rest as ScheminList) != null)
            {
                ScheminList temp = (ScheminList) rest;

                if (temp.Empty)
                {
                    return new ScheminList(head);
                }
                else
                {
                    ScheminList consd = new ScheminList(head);

                    foreach (IScheminType type in temp)
                    {
                        consd.Append(type);
                    }

                    return consd;
                }
            }

            var append = new ScheminList(head);
            append.Append(rest);
            return append;
        }
Пример #4
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            IScheminType toDisplay = args.Car();
            ScheminPort writeTo = eval.CurrentOutputPort;

            IScheminType port = args.Cdr().Car();
            if ((port as ScheminPort) != null)
            {
                writeTo = (ScheminPort) port;
            }

            if (toDisplay.GetType() == typeof(ScheminString))
            {
                ScheminString temp = (ScheminString) toDisplay;
                writeTo.OutputStream.Write(temp.Value);
                writeTo.OutputStream.Flush();
            }
            else
            {
                writeTo.OutputStream.Write(toDisplay.ToString());
                writeTo.OutputStream.Flush();
            }

            return new ScheminList(false);
        }
Пример #5
0
        public ScheminLambda(ScheminList definition, Environment closure)
        {
            this.Arguments = definition.Car();

            if (definition.Cdr().Length == 1)
            {
                this.Definition = definition.Cdr().Car();
            }
            else
            {
                ScheminList def = definition.Cdr();
                def.Cons(new ScheminPrimitive("begin"));
                this.Definition = def;
            }

            this.Closure = closure;
        }
Пример #6
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            bool deffun = false;

            if ((args.Car() as ScheminList) != null)
            {
                deffun = true;
            }

            if (!deffun)
            {
                ScheminAtom symbol = (ScheminAtom) args.Car();
                IScheminType definition = args.Cdr().Car();

                if (env.bindings.ContainsKey(symbol.Name))
                {
                    env.RemoveBinding(symbol);
                    env.AddBinding(symbol, definition);
                }
                else
                {
                    env.AddBinding(symbol, definition);
                }

                return new ScheminList(false);
            }
            else
            {
                ScheminList arguments = (ScheminList) args.Car();
                ScheminList expression = args.Cdr();

                ScheminAtom name = (ScheminAtom) arguments.Car();
                ScheminList argSymbols = arguments.Cdr();

                ScheminList lamArgs = new ScheminList(argSymbols, expression);
                lamArgs.UnQuote();

                ScheminLambda lam = new ScheminLambda(lamArgs, env);

                if (env.bindings.ContainsKey(name.Name))
                {
                    env.RemoveBinding(name);
                    env.AddBinding(name, lam);
                }
                else
                {
                    env.AddBinding(name, lam);
                }

                return new ScheminList(false);
            }
        }
Пример #7
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            ScheminChar first = (ScheminChar) args.Car();
            ScheminChar second = (ScheminChar) args.Cdr().Car();

            int result = first.Value.CompareTo(second.Value);

            if (result > 0)
            {
                return ScheminBool.True;
            }

            return ScheminBool.False;
        }
Пример #8
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            IScheminType function = args.Car();
            ScheminList argList = args.Cdr();
            ScheminList toApply = (ScheminList) args.Cdr().Last();

            ScheminList list = new ScheminList();
            list.UnQuote();

            foreach (IScheminType type in toApply)
            {
                list.Append(type);
            }

            foreach (IScheminType type in argList)
            {
                if (type != toApply)
                    list.Cons(type);
            }

            list.Cons(function);

            return list;
        }
Пример #9
0
        public override void CheckArguments(ScheminList args)
        {
            IScheminType first = args.Car();
            IScheminType second = args.Cdr().Car();

            if (args.Length != 2)
            {
                throw new BadArgumentsException("expected 2 arguments");
            }

            if ((first as IScheminNumeric) == null || (second as IScheminNumeric == null))
            {
                throw new BadArgumentsException("arguments must be numeric");
            }

            return;
        }
Пример #10
0
        public override void CheckArguments(ScheminList args)
        {
            IScheminType first = args.Car();
            IScheminType second = args.Cdr().Car();

            if (args.Length > 2 || args.Length < 1)
            {
                throw new BadArgumentsException("expected 1 or 2 arguments");
            }

            if ((first as ScheminInteger) == null)
            {
                throw new BadArgumentsException("first argument must be an integer");
            }

            return;
        }
Пример #11
0
        public override void CheckArguments(ScheminList args)
        {
            if (args.Length < 1 || args.Length > 2)
            {
                throw new BadArgumentsException("expected 1 or 2 arguments");
            }

            if (args.Length == 2)
            {
                IScheminType port = args.Cdr().Car();
                if ((port as ScheminPort) == null)
                {
                    throw new BadArgumentsException("second argument must be a port");
                }
            }

            return;
        }
Пример #12
0
        public override void CheckArguments(ScheminList args)
        {
            IScheminType first = args.Car();
            IScheminType last = args.Cdr().Last();

            if ((first as ScheminPrimitive) == null && (first as ScheminLambda) == null
            && (first as ScheminContinuation) == null && (first as ScheminRewriter) == null)
            {
                throw new BadArgumentsException("first argument must be a procedure");
            }

            if ((last as ScheminList) == null)
            {
                throw new BadArgumentsException("last argument must be a list");
            }

            return;
        }
Пример #13
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            IScheminNumeric first = (IScheminNumeric) args.Car();
            IScheminNumeric second = (IScheminNumeric) args.Cdr().Car();

            if ((first as ScheminDecimal) != null || (second as ScheminDecimal) != null)
            {
                if (first.DecimalValue() < second.DecimalValue())
                {
                    return ScheminBool.True;
                }
            }
            else
            {
                if (first.IntegerValue() < second.IntegerValue())
                {
                    return ScheminBool.True;
                }
            }

            return ScheminBool.False;
        }
Пример #14
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            ScheminAtom symbol = (ScheminAtom) args.Car();
            IScheminType definition = args.Cdr().Car();

            Environment parent = env;
            while (parent != null)
            {
                IScheminType value;
                parent.bindings.TryGetValue(symbol.Name, out value);

                if (value != null)
                {

                    parent.RemoveBinding(symbol);
                    parent.AddBinding(symbol, definition);
                    return new ScheminList(false);
                }

                parent = parent.parent;
            }

            throw new UnboundAtomException(string.Format("Unbound atom: {0}", symbol));
        }
Пример #15
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            ScheminInteger len = (ScheminInteger) args.Car();
            IScheminType init = args.Cdr().Car();

            ScheminVector vec = new ScheminVector();
            if (args.Length == 1)
            {
                ScheminList empty = new ScheminList(true);
                for (int i = 0; i < len.IntegerValue(); i++)
                {
                    vec.List.Add(empty);
                }
            }
            else
            {
                for (int i = 0; i < len.IntegerValue(); i++)
                {
                    vec.List.Add(init);
                }
            }

            return vec;
        }
Пример #16
0
        public IScheminType EvaluateList(ScheminList list)
        {
            StackFrame start = new StackFrame();
            start.WaitingOn = list;
            start.CurrentEnv = this.GlobalEnv;

            Stack.Clear();
            Stack.Push(start);

            StackStart:
            while (Stack.Count > 0)
            {
                StackFrame current = Stack.Pop();
                Environment CurrentEnv = current.CurrentEnv;

                ScheminList before = current.Before;
                ScheminList after = current.After;
                IScheminType WaitingOn = current.WaitingOn;

                if ((WaitingOn as ScheminList) == null || WaitingOn.Quoted() == true || IsEmptyList(WaitingOn))
                {
                    StackFrame next = new StackFrame();

                    if (before == null && after == null)
                    {
                        if ((WaitingOn as ScheminAtom) != null && !WaitingOn.Quoted())
                        {
                            WaitingOn = EvalAtom(WaitingOn, CurrentEnv);
                        }

                        if (Stack.Count < 1)
                        {
                            return WaitingOn;
                        }

                        StackFrame previous = Stack.Pop();
                        if (previous.Before == null && previous.After == null)
                        {
                            next.WaitingOn = WaitingOn;
                        }
                        else
                        {
                            next.WaitingOn = CombineStackFrame(previous.Before, previous.After, WaitingOn);
                        }

                        // Use the previous environment in this case as well
                        if (Stack.Count > 0)
                        {
                            next.CurrentEnv = Stack.Peek().CurrentEnv;
                        }
                        else
                        {
                            next.CurrentEnv = previous.CurrentEnv;
                        }

                        Stack.Push(next);
                        continue;
                    }

                    // We need to use the PREVIOUS environment here, so peek it.. otherwise we're re-using the same environment for the previous context.
                    StackFrame peeked = Stack.Peek();
                    next.WaitingOn = CombineStackFrame(before, after, WaitingOn);
                    next.CurrentEnv = peeked.CurrentEnv;
                    Stack.Push(next);
                    continue;
                }

                StackFrame completeFrame = new StackFrame();
                ScheminPrimitive currentPrimitive = null;

                ScheminList rest = (ScheminList) WaitingOn;
                ScheminList pendingBefore = new ScheminList();
                pendingBefore.UnQuote();

                if ((rest.Car() as ScheminPrimitive) != null)
                {
                    if (rest.Car().Quoted() == false)
                    {
                        currentPrimitive = (ScheminPrimitive) rest.Car();
                    }
                }

                int currentArg = 0;

                while (!rest.Empty)
                {
                    IScheminType type = rest.Car();

                    if (currentPrimitive != null)
                    {
                        if (!EvaluateNextArg(currentPrimitive, currentArg, ((ScheminList) WaitingOn).Cdr()))
                        {
                            pendingBefore.Append(type);
                            rest = rest.Cdr();
                            currentArg++;
                            continue;
                        }
                    }

                    if ((type as ScheminAtom) != null)
                    {
                        if (type.Quoted())
                        {
                            pendingBefore.Append(type);
                        }
                        else
                        {
                            IScheminType atomResult = EvalAtom(type, CurrentEnv);
                            if ((atomResult as ScheminRewriter) != null)
                            {
                                // if we get a quoted rewriter here, we're going to apply it :(
                                pendingBefore.Append(atomResult);
                                QuoteAll(rest.Cdr());
                            }
                            else
                            {
                                pendingBefore.Append(atomResult);
                            }
                        }
                    }
                    else if ((type as ScheminList) != null)
                    {
                        ScheminList tempList = (ScheminList) type;

                        if (tempList.Quoted() || tempList.Empty)
                        {
                            pendingBefore.Append(type);
                            rest = rest.Cdr();
                            currentArg++;
                            continue;
                        }

                        StackFrame next = new StackFrame();
                        next.WaitingOn = type;
                        next.After = rest.Cdr();
                        next.Before = pendingBefore;
                        next.CurrentEnv = CurrentEnv;

                        Stack.Push(current);
                        Stack.Push(next);

                        goto StackStart;
                    }
                    else
                    {
                        pendingBefore.Append(type);
                    }

                    rest = rest.Cdr();
                    currentArg++;
                }

                IScheminType functionPosition = pendingBefore.Car();
                ScheminList functionArgs = pendingBefore.Cdr();

                if ((functionPosition as ScheminPrimitive) != null)
                {
                    ScheminPrimitive prim = (ScheminPrimitive) functionPosition;
                    completeFrame.Before = before;
                    completeFrame.After = after;

                    // Need to pass push the previous frame back on so we can get access to the current continuation via the evaluator's Stack field.
                    // also adding the primitive's name to the exception if it gets thrown.
                    try
                    {
                        Stack.Push(current);
                        completeFrame.WaitingOn = prim.Evaluate(functionArgs, CurrentEnv, this);
                        Stack.Pop();
                    }
                    catch (BadArgumentsException ba)
                    {
                        Token sourceToken = prim.SourceToken;
                        string line = String.Empty;
                        if (sourceToken != null)
                        {
                            line = " line: " + sourceToken.LineNumber.ToString() + " col: " + sourceToken.ColNumber.ToString();
                        }
                        throw new BadArgumentsException(prim.ToString() + " " + ba.Message + line);
                    }

                    completeFrame.CurrentEnv = CurrentEnv;

                    Stack.Push(completeFrame);
                    continue;
                }
                else if ((functionPosition as ScheminLambda) != null)
                {
                    ScheminLambda lam = (ScheminLambda) functionPosition;
                    completeFrame.Before = before;
                    completeFrame.After = after;

                    Environment args = lam.MakeEnvironment(functionArgs, this);
                    completeFrame.WaitingOn = lam.Definition;
                    completeFrame.CurrentEnv = args;

                    Stack.Push(completeFrame);
                    continue;
                }
                else if ((functionPosition as ScheminContinuation) != null)
                {
                    ScheminContinuation con = (ScheminContinuation) functionPosition;
                    this.Stack = new Stack<StackFrame>(con.PreviousStack);
                    this.Stack.Peek().WaitingOn = functionArgs.Car();
                    continue;
                }
                else if ((functionPosition as ScheminRewriter) != null)
                {
                    ScheminRewriter rewriter = (ScheminRewriter) functionPosition;

                    QuoteAll(functionArgs);
                    IScheminType result = rewriter.Rewrite(functionArgs);

                    completeFrame.Before = before;
                    completeFrame.After = after;
                    completeFrame.WaitingOn = result;
                    completeFrame.CurrentEnv = CurrentEnv;

                    this.Stack.Push(completeFrame);
                    continue;
                }
                else
                {
                    throw new InvalidOperationException("Non-function in function position: " + functionPosition.ToString());
                }
            }

            throw new InvalidOperationException("Control escaped list evaluator...");
        }
Пример #17
0
        public Environment MakeEnvironment(ScheminList values, Evaluator eval)
        {
            if ((this.Arguments as ScheminList) != null)
            {
                ScheminList argslist = (ScheminList) this.Arguments;
                IScheminType first = argslist.Car();
                ScheminList rest = argslist.Cdr();
                IScheminType firstArg = values.Car();
                ScheminList restArgs = values.Cdr();

                Environment args = new Environment();
                args.parent = this.Closure;

                for (; ;)
                {
                    if (first.GetType() == typeof(ScheminList))
                    {
                        ScheminList tempFirst = (ScheminList) first;
                        if (tempFirst.Empty)
                        {
                            break;
                        }
                    }

                    ScheminAtom atom = (ScheminAtom) first;
                    if (atom.Name == ".")
                    {
                        restArgs.Cons(firstArg);
                        restArgs.Quote();
                        args.AddBinding((ScheminAtom) rest.Car(), restArgs);
                        break;
                    }

                    args.AddBinding((ScheminAtom) first, firstArg);

                    first = rest.Car();
                    firstArg = restArgs.Car();
                    rest = rest.Cdr();
                    restArgs = restArgs.Cdr();
                }

                return args;
            }
            else
            {
                Environment args = new Environment();
                args.parent = this.Closure;
                values.Quote();
                args.AddBinding((ScheminAtom) this.Arguments, values);
                return args;
            }
        }
Пример #18
0
        public override IScheminType Execute(Environment env, Evaluator eval, ScheminList args)
        {
            bool isNamed = false;
                if ((args.Car() as ScheminAtom) != null)
                {
                    isNamed = true;
                }

                ScheminList bindings;
                ScheminList expression;

                if (!isNamed)
                {
                    expression = args.Cdr();
                    bindings = (ScheminList) args.Car();
                }
                else
                {
                    expression = args.Cdr().Cdr();
                    bindings = (ScheminList) args.Cdr().Car();
                }

                ScheminList letArgs = new ScheminList();
                ScheminList argExps = new ScheminList();

                letArgs.UnQuote();
                argExps.UnQuote();

                foreach (ScheminList bindingPair in bindings)
                {
                    letArgs.Append(bindingPair.Car());
                    argExps.Append(bindingPair.Cdr().Car());
                }

                ScheminList lambdaDef = new ScheminList(letArgs);
                lambdaDef.UnQuote();

                foreach (IScheminType type in expression)
                {
                    lambdaDef.Append(type);
                }

                Environment closure = env;
                if (isNamed)
                {
                    closure = new Environment();
                    closure.parent = env;
                }

                ScheminLambda lam = new ScheminLambda(lambdaDef, closure);

                if (isNamed)
                {
                    ScheminAtom name = (ScheminAtom) args.Car();
                    closure.AddBinding(name, lam);
                }

                ScheminList toEvaluate = new ScheminList(lam);
                toEvaluate.UnQuote();

                foreach (IScheminType arg in argExps)
                {
                    toEvaluate.Append(arg);
                }

                return toEvaluate;
        }