internal LoxFunction bind(LoxInstance instance)
        {
            Envir envir = new Envir(Closure);

            envir.define("this", instance);
            return(new LoxFunction(Declaration, envir, IsInitializer));
        }
 public LoxFunction(Stmt.Function declaration, Envir closure,
                    bool isInitializer)
 {
     IsInitializer = isInitializer;
     Closure       = closure;
     Declaration   = declaration;
 }
Beispiel #3
0
        Envir ancestor(int distance)
        {
            Envir envir = this;

            for (int i = 0; i < distance; i++)
            {
                envir = envir.Enclosing;
            }
            return(envir);
        }
        public void executeBlock(List <Stmt> statements, Envir envir)
        {
            Envir previous = env;

            try {
                env = envir;
                foreach (var s in statements)
                {
                    execute(s);
                }
            } finally {
                env = previous;
            }
        }
        public object visitClassStmt(Stmt.Class stmt)
        {
            object superClass = null;

            if (stmt.SuperClass != null)
            {
                superClass = evaluate(stmt.SuperClass);
                if (!(superClass is LoxClass))
                {
                    throw new RuntimeError(stmt.SuperClass.Name,
                                           "Superclass must be a class.");
                }
            }

            env.define(stmt.Name.Lexeme, null);

            if (stmt.SuperClass != null)
            {
                env = new Envir(env);
                env.define("super", superClass);
            }

            Dictionary <string, LoxFunction> methods = new Dictionary <string, LoxFunction>();

            foreach (Stmt.Function method in stmt.Methods)
            {
                LoxFunction function = new LoxFunction(method, env,
                                                       method.Name.Lexeme == "init");
                methods[method.Name.Lexeme] = function;
            }

            LoxClass klass = new LoxClass(stmt.Name.Lexeme,
                                          (LoxClass)superClass, methods);


            if (stmt.SuperClass != null)
            {
                env = env.Enclosing;
            }

            env.assign(stmt.Name, klass);
            return(null);
        }
        public object call(Interpreter interpreter, List <object> args)
        {
            Envir envir = new Envir(Closure);

            for (int i = 0; i < Declaration.Parameters.Count; i++)
            {
                envir.define(Declaration.Parameters[i].Lexeme, args[i]);
            }
            try {
                interpreter.executeBlock(Declaration.Body, envir);
            } catch (LoxReturn returnValue) {
                if (IsInitializer)
                {
                    return(Closure.getAt(0, "this"));
                }
                return(returnValue.Value);
            }
            if (IsInitializer)
            {
                return(Closure.getAt(0, "this"));
            }
            return(null);
        }
 public Interpreter()
 {
     env = globals;
     globals.define("clock", new Functions.ClockFunction());
 }
Beispiel #8
0
 public Envir()
 {
     Enclosing = null;
     Values    = new Dictionary <string, object>();
 }
Beispiel #9
0
 public Envir(Envir enclosing)
 {
     Enclosing = enclosing;
     Values    = new Dictionary <string, object>();
 }