class Base {
private int i = 2; // 2
public Base() {
this.display(); // 3
}
public void display() {
System.out.println(i); //
}
}
class Derived extends Base {
private int i = 22; // 5
public Derived() {
i = 222; // 6
}
public void display() {
System.out.println(i); // 4
}
}
public class Test {
public static void main(String[] args) {
new Derived(); // 1
}
}
以上代码输出结果为0
代码行的注释表示执行顺序;
1:系统先为Derived对象分配内存空间,有两块内存空间分别存放Derived对象的两个i实例变量,一个是属于Base的一个是Derived的,此时这两个i实例变量的值都是0;
2:执行Derived类的构造器之前,先执行Base类的构造器。表面上看,Base类经过编译器处理后,其构造器包含如下两行代码:
i = 2;
this.display();
3: this.display();中的this在这里是指向Derived的,即实现子类的方法覆盖父类的方法
4:此时Derived的i还没有经过初始化,为0,故输出0
5:Derived的i初始化
6:Derived的构造器
----------------------------------
将Base类的构造器改为如下形式:
public Base() {
System.out.println(this.i);
this.display();
}
再次运行程序,将看到输出是2和0;
当变量的编译时类型和运行时类型不同时,通过该变量访问它所引用的对象的实例变量时,该实例变量的值由声明该变量的类型决定,但通过该变量调用它引用的对象的实例方法时,该方法行为由它实际所引用的对象来决定,一次当程序访问this.i时,它将访问Base类中定义的i实例变量,也就是将输出2;但执行 this.display()时则实际表现出Derived对象的行为,也就是输出Derived对象的i实例变量,即为0。
分享到:
相关推荐
在运行时,当我们调用对象的方法时,JVM 会根据对象的实际类型来查找相应的方法,并调用该方法。 例如,在 Java 中,我们可以定义一个抽象类 Animal,它具有一个抽象方法 enjoy: ```java abstract class Animal {...
这种类型的注解不会在运行时保留,它们的作用是在编译期间执行一些处理,如代码生成、验证等。在Android中,我们通常使用Java的`@Retention(RetentionPolicy.CLASS)`或`@Retention(RetentionPolicy.SOURCE)`策略来...
4. **多线程与并发**:运行时环境支持多线程和并发执行,允许多个任务同时进行,提升程序性能。 5. **动态绑定**:面向对象编程中的动态绑定,即方法调用在运行时确定,而非编译时,这允许了更多的灵活性,如多态性...
题,给出了基于运行时信息指针辅助判定方法,同时针对基本类型重构结果不确定的情况, 给出了基于数据流分析框架的双向类型传播模型,通过构建类型格并在格的基础上求解类 型传播方程,从而达到类型细化的目的;通过...
C++17引入了一些新的特性,使得实现不可变的编译时键值映射变得更加便捷。下面将详细讨论这个主题。 首先,C++17中的`std::variant`和`std::any`是实现编译时键值映射的重要工具。`std::variant`允许我们存储多种...
当Spring容器找不到匹配的bean时,可以通过指定类型或名称来精确控制注入。 2. `@Qualifier`:配合`@Autowired`使用,用于在多个相同类型的bean中指定具体要注入哪一个。 3. `@Component`、`@Service`、`@...
这个插件可能是Babel的一个扩展,它在Babel编译代码的过程中添加了运行时类型检查的功能。通过在编译阶段集成类型检查,可以在开发阶段就发现类型错误,而不是等到生产环境。 在JavaScript开发中,运行时类型检查有...
【 Turbo Pascal 编译错误与运行错误信息中英文对照详解】 在编程过程中,理解并解决编译错误和运行错误是至关重要的。对于使用 Turbo Pascal 的开发者来说,掌握这些错误信息的含义能帮助我们更快地定位问题,提高...
eclipse 中编译、运行都正常,但是如果用maven的打包命令 mvn clean package 进行打包时会发现有类型错误
课程主要涵盖了.NET Framework的手动编译、运行时环境(Common Language Runtime,简称CLR)、语言互操作性规范(Common Language Specification,简称CLS)、类型系统(Common Type System,简称CTS)以及Just-In-...
编译时注解,顾名思义,就是这些注解在编译阶段起作用,它们对程序的运行时行为没有直接影响,但能帮助编译器进行检查或生成额外的辅助文件。 ## 1. 注解类型 Java中的注解分为三种类型:源码保留(Source ...
运行时类型检查与编译时类型检查不同,运行时类型检查是指代码在执行时对类型的检查。 在运行时,代码可能会遇到一些错误,如数组越界、空指针等错误。这些错误在编译时可能不容易发现,但是可以在运行时发现并报告...
在编译开始之前,C#编译器会进行预处理,这包括处理#define、#if、#else、#endif等预处理器指令,它们允许程序员在编译时条件化地包含或排除代码块。 3. **词法分析与语法分析** 词法分析器(Scanner)将源代码...
当我们需要查看已编译的.class文件的源代码时,就需要反编译工具。Java的反编译工具有很多,如JAD、JD-GUI等。本工具集成了这一功能,可以将.class文件转换回.java源代码,帮助开发者理解已有的代码或逆向工程。 四...
2. **类型不匹配**:当程序中两个操作数的类型不兼容时,例如整型与浮点型相加,或者未定义的数据类型,会出现此类错误。 3. **变量未声明**:如果在使用变量之前未进行声明,编译器会报错。 4. **函数调用错误**...
1. 静态类型检查:在编译阶段进行类型检查,防止运行时错误,增强代码的可靠性和安全性。 2. 动态类型系统:允许在运行时动态地绑定类型,提供了更大的灵活性,但可能增加运行时错误的风险。 3. 编译器优化技术:...
- **类型不匹配**:当函数调用时传递的参数类型与函数声明中指定的类型不一致时,会发生此类错误。 - **解决方案**:检查函数声明和实际调用之间的参数类型一致性,并作出相应的修改。 - **内存溢出**:当程序...
当整数运算超出其数据类型范围时,开启此选项会在运行时抛出异常。 7. **/codepage** 指定编码页,确保源代码文件的字符集正确解析。 8. **/debug** 生成调试信息,这对于使用调试器进行程序调试至关重要。 9. ...
但是,这种方法的缺点在于枚举类型不能包含复杂的数据结构。 2. 接口继承:通过让多个类实现同一个接口,可以创建一个虚拟的联合类型。每个类代表一个类型,而接口则表示这些类型共享的行为。然而,这种方法无法...
总结来说,C#动态执行与编译是.NET框架提供的一系列强大工具和API的集合,它们允许开发者在运行时生成、编译和执行代码,极大地提高了代码的灵活性和适应性。无论是通过`System.Reflection.Emit`的低级别操作,还是...