运行时和编译时的区别是什么?


当前回答

作为其他答案的补充,以下是我对外行的解释:

您的源代码就像一艘船的蓝图。它定义了船应该如何制造。

如果你把你的蓝图交给造船厂,他们在建造船的时候发现了一个缺陷,他们会立即停止建造并向你报告,在船离开干船坞或接触水之前。这是一个编译时错误。这艘船甚至从未真正漂浮过,也没有使用过它的引擎。这个错误之所以被发现,是因为它甚至阻止了这艘船的制造。

当您的代码编译完成时,就像船完成了一样。建好了,可以出发了。当你执行你的代码时,就像在航行中让船下水一样。乘客上了船,引擎在运转船体在水面上,这是运行时间。如果你的船有致命的缺陷,在处女航时就沉没了(或者可能是一些额外的麻烦),那么它就遇到了运行错误。

其他回答

基本上,如果你的编译器能在“编译时”找出你的意思或一个值是什么,它就能硬编码到运行时代码中。显然,如果你的运行时代码每次都要进行计算,那么它会运行得更慢,所以如果你能在编译时确定一些东西,那就更好了。

Eg.

常数合并:

如果我这样写:

int i = 2;
i += MY_CONSTANT;

编译器可以在编译时执行这个计算,因为它知道2是什么,MY_CONSTANT是什么。因此,每次执行时,它都不必执行计算。

运行时是指在运行程序时发生的事情。

编译时是指在编译程序时发生的事情。

我一直认为它与程序处理开销以及它如何影响性能有关,如前所述。一个简单的例子是,在代码中定义对象所需的绝对内存。

一个定义的布尔值占用x个内存,然后在编译后的程序中,不能更改。当程序运行时,它确切地知道为x分配多少内存。

另一方面,如果我只是定义了一个泛型对象类型(即一种未定义的占位符或可能是一个指向一些巨大blob的指针),我的对象所需的实际内存是不知道的,直到程序运行,我分配了一些东西给它,因此它必须评估和内存分配等,然后将在运行时动态处理(更多的运行时开销)。

如何动态处理它取决于语言、编译器、操作系统、你的代码等等。

然而,在这一点上,它实际上取决于您使用运行时和编译时的上下文。

我们可以将其分为两大类静态绑定和动态绑定。它取决于何时与相应值绑定。如果引用是在编译时解析的,那么它是静态绑定;如果引用是在运行时解析的,那么它是动态绑定。静态绑定和动态绑定又称早期绑定和后期绑定。有时也称为静态多态和动态多态。

约瑟夫Kulandai‏。

public class RuntimeVsCompileTime {

    public static void main(String[] args) {
        
        //test(new D()); COMPILETIME ERROR
        /**
         * Compiler knows that B is not an instance of A
         */
        test(new B());
    }
    
    /**
     * compiler has no hint whether the actual type is A, B or C
     * C c = (C)a; will be checked during runtime
     * @param a
     */
    public static void test(A a) {
        C c = (C)a;//RUNTIME ERROR
    }

}

    class A{
    
}

    class B extends A{
    
}

    class C extends A{
    
}

    class D{
    
}