美文网首页
clojure eval compile

clojure eval compile

作者: onedam | 来源:发表于2021-03-09 17:36 被阅读0次

    无论 eval 还是 直接 compile 都生成了jvm字节码类. compile 会在磁盘上生成文件. eval
    直接load 不会生成类.

    public static Object eval(Object form, boolean freshLoader) {
        boolean createdLoader = false;
        if(true)//!LOADER.isBound())
            {
            Var.pushThreadBindings(RT.map(LOADER, RT.makeClassLoader()));
            createdLoader = true;
            }
        try
            {
            IPersistentMap meta = RT.meta(form);
            Object line = (meta != null ? meta.valAt(RT.LINE_KEY, LINE.deref()) : LINE.deref());
            Object column = (meta != null ? meta.valAt(RT.COLUMN_KEY, COLUMN.deref()) : COLUMN.deref());
            IPersistentMap bindings = RT.mapUniqueKeys(LINE, line, COLUMN, column);
            if(meta != null) {
                Object eval_file = meta.valAt(RT.EVAL_FILE_KEY);
                if(eval_file != null) {
                    bindings = bindings.assoc(SOURCE_PATH, eval_file);
                    try {
                        bindings = bindings.assoc(SOURCE, new File((String)eval_file).getName());
                    } catch (Throwable t) {
                    }
                }
            }
            Var.pushThreadBindings(bindings);
            try
                {
                form = macroexpand(form);
                if(form instanceof ISeq && Util.equals(RT.first(form), DO))
                    {
                    ISeq s = RT.next(form);
                    for(; RT.next(s) != null; s = RT.next(s))
                        eval(RT.first(s), false);
                    return eval(RT.first(s), false);
                    }
                else if((form instanceof IType) ||
                        (form instanceof IPersistentCollection
                        && !(RT.first(form) instanceof Symbol
                            && ((Symbol) RT.first(form)).name.startsWith("def"))))
                    {
                    ObjExpr fexpr = (ObjExpr) analyze(C.EXPRESSION, RT.list(FN, PersistentVector.EMPTY, form),
                                                        "eval" + RT.nextID());
                    IFn fn = (IFn) fexpr.eval();
                    return fn.invoke();
                    }
                else
                    {
                    Expr expr = analyze(C.EVAL, form);
                    return expr.eval();  //需要返回
                    }
                }
            finally
                {
                Var.popThreadBindings();
                }
            }
    
        finally
            {
            if(createdLoader)
                Var.popThreadBindings();
            }
    }
    
    static void compile1(GeneratorAdapter gen, ObjExpr objx, Object form) {
        Object line = lineDeref();
        Object column = columnDeref();
        if(RT.meta(form) != null && RT.meta(form).containsKey(RT.LINE_KEY))
            line = RT.meta(form).valAt(RT.LINE_KEY);
        if(RT.meta(form) != null && RT.meta(form).containsKey(RT.COLUMN_KEY))
            column = RT.meta(form).valAt(RT.COLUMN_KEY);
        Var.pushThreadBindings(
                RT.map(LINE, line, COLUMN, column
                       ,LOADER, RT.makeClassLoader()
                ));
        try
            {
            form = macroexpand(form);
            if(form instanceof ISeq && Util.equals(RT.first(form), DO))
                {
                for(ISeq s = RT.next(form); s != null; s = RT.next(s))
                    {
                    compile1(gen, objx, RT.first(s));
                    }
                }
            else
                {
                Expr expr = analyze(C.EVAL, form);
                objx.keywords = (IPersistentMap) KEYWORDS.deref();
                objx.vars = (IPersistentMap) VARS.deref();
                objx.constants = (PersistentVector) CONSTANTS.deref();
                expr.emit(C.EXPRESSION, objx, gen);
                expr.eval();      // 不需要返回 ,但 eval 和compile 都会 eval .
                                                   //这就是clojure文件中写了调用函数都会执行的原因
                }
            }
        finally
            {
            Var.popThreadBindings();
            }
    }
    

    相关文章

      网友评论

          本文标题:clojure eval compile

          本文链接:https://www.haomeiwen.com/subject/czhbqltx.html