java基础面试题
- 1.short s1 = 1;s1 = s1 + 1;有什么错?那么 short s1 = 1; s1 += 1呢?有没有错误?
- 2.Integer 和 int 的区别?
- 3.Integer与int
- 4.自动装箱与拆箱
- 5.switch 语句能否作用在 byte 上,能否作用在 long 上,能否作用在 String 上?
- 6.字节和字符的区别
- 7.String,StringBuilder,StringBuffer的区别
- 8.String 字符串修改实现的原理?
- 9.String str = "i" 与 String str = new String("i") 一样吗?
- 10.String 类的常用方法都有那些?
- 11.区分以下两种情况
- 12.final 修饰 StringBuffer 后还可以 append 吗?
- 13.Object 的常用方法有哪些?
- 14.为什么 wait/notify 方法放在 Object 类中而不是 Thread 类中?
- 15.final、finally、finalize 的区别?
- 16.finally 块中的代码什么时候被执行?
- 17.finally 是不是一定会被执行到?
- 18.try-catch-finally 中那个部分可以省略?
- 19.try-catch-finally 中,如果 catch 中 return 了,finally 还会执行吗?
- 20.static 关键字的作用?
- 21.super 关键字的作用?
- 22.transient关键字的作用?
- 23.== 和 equals 的区别?
- 24.两个对象的 hashCode() 相同,则 equals() 也一定为 true 吗?
- 25.为什么重写 equals() 就一定要重写 hashCode() 方法?
- 26.& 和 && 的区别?
- 27.Java 中的参数传递时传值呢?还是传引用?
- 28.Java 中的 Math.round(-1.5) 等于多少?
- 29.两个二进制数的异或结果是什么?
- 30.Error 和 Exception 的区别?
- 31.运行时异常与受检异常有何异同?
- 32.throw 和 throws 的区别?
- 33.常见的异常类有哪些?
- 34.主线程可以捕获到子线程的异常吗?
- 35.Java 的泛型是如何工作的 ? 什么是类型擦除 ?
- 36.什么是泛型中的限定通配符和非限定通配符 ?
- 37.如何实现对象的克隆?
- 38.深克隆和浅克隆的区别?
- 39.静态变量和实例变量的区别?
- 40.抽象类和接口有什么区别?
- 41.Java 中创建对象的几种方式?
- 42.在 Java 中定义一个不做事且没有参数的构造方法有什么作用?
- 43.构造方法有哪些特性?
- 44.构造器是否可以被重写?
- 45.Java 中是否可以重写一个 private 或者 static 方法?
- 46.重载和重写的区别?
- 47.JDK、JRE、JVM 三者之间的关系?
- 48.面向对象的三大特性?分别解释下?
- 49.解释下什么是面向对象?面向对象和面向过程的区别?
1.short s1 = 1;s1 = s1 + 1;有什么错?那么 short s1 = 1; s1 += 1呢?有没有错误?
答:第一个有错。java规范:高类型向低类型转换需要强制转换,低类型向高类型转换是自动的。s1+1通过+运算符将右边的s1转换为int型,而左边s1为short型,需要进行强制转换,否则编译会出现错误。
注:为啥编译会出现错误,试想左边short为2字节,右边int为4字节,将4字节的东西放在2字节里,编译肯定不能通过
第二个编译成功。第二个与第一个的区别是s1+=1属于复合赋值表达式,而s1=s1+1属于简单赋值表达式,复合赋值E1 op= E2等价于简单赋值E1=(T)(E1 op E2),T是E1的类型
链接: https://www.jianshu.com/p/305060207bde.
2.Integer 和 int 的区别?
答:(1)int 是 Java 的八种基本数据类型之一,而 Integer 是 Java 为 int 类型提供的封装类;
(2)int 型变量的默认值是 0,Integer 变量的默认值是 null,这一点说明 Integer 可以区分出未赋值和值为 0 的区分;
(3)Integer 变量必须实例化后才可以使用,而 int 不需要。
3.Integer与int
public class q_1 {
public static void main(String[] args){
Integer a=new Integer(4);
Integer b=4;
if(a==b) {
System.out.print("相等");
}
else {
System.out.print("不相等");
}
}
}
输出结果为:不相等
答:非new生成的Integer变量和new生成的Integer变量进行比较时,结果都为false。因为非new生成的Integer变量指向的是Java常量池中的对象,而new生成的Integer变量指向的是堆中新建的对象,两者在内存中的地址不相同。
public static void main(String[] args){
Integer a=new Integer(4);
Integer b=new Integer(4);
if(a==b) {
System.out.print("相等");
}
else {
System.out.print("不相等");
}
}
输出结果为:不相等
答:两个通过new生成的Integer变量永远是不相等的,因为其内存地址不相等。
public static void main(String[] args){
Integer a=new Integer(4);
Integer b=new Integer(4);
if(a.equals(b)) {
System.out.print("相等");
}
else {
System.out.print("不相等");
}
}
输出结果为:相等
4.自动装箱与拆箱
答:自动装箱:java编译器在基本数据类型与对应的包装类之间的一个转换
反之就是拆箱。
5.switch 语句能否作用在 byte 上,能否作用在 long 上,能否作用在 String 上?
答:switch(expr 1)中,expr1只能是一个整数表达式或者枚举常量。而整数表达式可以是int 基本数据类型或者Integer包装类型。由于,byte,short,char都可以隐式转换为int,而long和String类型都不符合switch的语法规定。
需要注意的是在JDK1.7版本之后switch就可以作用在String上
6.字节和字符的区别
答;字节是存储容量的基本单位
1字节=8个二进制单位,一个字符由一个字节或多个字节的二进制单位组成
7.String,StringBuilder,StringBuffer的区别
答:String:用于字符串操作,属于不可变类
StringBuilder:字符串缓冲区,属于可变类,线程不安全
StringBuffer:字符串缓冲区,属于可变类,对方法加了同步锁,线程安全
执行效率:StringBuilder>StringBuffer>String
8.String 字符串修改实现的原理?
答:当用 String 类型来对字符串进行修改时,其实现方法是首先创建一个 StringBuffer,其次调用 StringBuffer 的 append() 方法,最后调用 StringBuffer 的 toString() 方法把结果返回。
9.String str = “i” 与 String str = new String(“i”) 一样吗?
答:不一样,因为内存的分配方式不一样。String str = “i” 的方式,Java 虚拟机会将其分配到常量池中;而 String str = new String(“i”) 则会被分到堆内存中。
10.String 类的常用方法都有那些?
答:indexOf():返回指定字符的索引。
charAt():返回指定索引处的字符。
replace():字符串替换。
trim():去除字符串两端空白。
split():分割字符串,返回一个分割后的字符串数组。
getBytes():返回字符串的 byte 类型数组。
length():返回字符串长度。
toLowerCase():将字符串转成小写字母。
toUpperCase():将字符串转成大写字符。
substring():截取字符串。equals():字符串比较。
11.区分以下两种情况
12.final 修饰 StringBuffer 后还可以 append 吗?
答:可以。final 修饰的是一个引用变量(对象型变量的本质),那么这个引用始终只能指向这个对象,但是这个对象内部的属性是可以变化的。
链接: https://blog.youkuaiyun.com/zgrgfr/article/details/56278643
13.Object 的常用方法有哪些?
答:clone 方法:用于创建并返回当前对象的一份拷贝;
getClass 方法:用于返回当前运行时对象的 Class;
toString 方法:返回对象的字符串表示形式;
finalize 方法:实例被垃圾回收器回收时触发的方法;
equals 方法:用于比较两个对象的内存地址是否相等,一般需要重写;hashCode 方法:用于返回对象的哈希值;
notify 方法:唤醒一个在此对象监视器上等待的线程。如果有多个线程在等待只会唤醒一个。
notifyAll 方法:作用跟 notify() 一样,只不过会唤醒在此对象监视器上等待的所有线程,而不是一个线程。
wait 方法:让当前对象等待;
14.为什么 wait/notify 方法放在 Object 类中而不是 Thread 类中?
答:一个很明显的原因是 Java 提供的锁是对象级的而不是线程级的,每个对象都有锁,通过线程获得。如果线程需要等待某些锁,那么调用对象中的 wait() 方法就有意义了。如果 wait() 方法定义在 Thread 类中,线程正在等待的是哪个锁就不明显了。简单的说,由于 wait,notify 和 notifyAll 都是锁级别的操作,所以把他们定义在 Object 类中因为锁属于对象。
15.final、finally、finalize 的区别?
答:final:用于声明属性、方法和类,分别表示属性不可变、方法不可覆盖、被其修饰的类不可继承;
finally:异常处理语句结构的一部分,表示总是执行;
finallize:Object类的一个方法,在垃圾回收时会调用被回收对象的finalize。
16.finally 块中的代码什么时候被执行?
答:在 Java 语言的异常处理中,finally 块的作用就是为了保证无论出现什么情况,finally 块里的代码一定会被执行。由于程序执行 return 就意味着结束对当前函数的调用并跳出这个函数体,因此任何语句要执行都只能在 return 前执行(除非碰到 exit 函数),因此 finally 块里的代码也是在 return 之前执行的。
此外,如果 try-finally 或者 catch-finally 中都有 return,那么 finally 块中的 return 将会覆盖别处的 return 语句,最终返回到调用者那里的是 finally 中 return 的值。
17.finally 是不是一定会被执行到?
答:不一定。下面列举两种执行不到的情况:
(1)当程序进入 try 块之前就出现异常时,会直接结束,不会执行 finally 块中的代码;
(2)当程序在 try 块中强制退出时也不会去执行 finally 块中的代码,比如在 try 块中执行 exit 方法。
18.try-catch-finally 中那个部分可以省略?
答:catch 可以省略。try 只适合处理运行时异常,try+catch 适合处理运行时异常+普通异常。也就是说,如果你只用 try 去处理普通异常却不加以 catch 处理,编译是通不过的,因为编译器硬性规定,普通异常如果选择捕获,则必须用 catch 显示声明以便进一步处理。而运行时异常在编译时没有如此规定,所以 catch 可以省略,你加上 catch 编译器也觉得无可厚非。
19.try-catch-finally 中,如果 catch 中 return 了,finally 还会执行吗?
答:会。程序在执行到 return 时会首先将返回值存储在一个指定的位置,其次去执行 finally 块,最后再返回。因此,对基本数据类型,在 finally 块中改变 return 的值没有任何影响,直接覆盖掉;而对引用类型是有影响的,返回的是在 finally 对 前面 return 语句返回对象的修改值。
20.static 关键字的作用?
(1)静态变量:又称为类变量,也就是说这个变量属于类的,类所有的实例都共享静态变量,可以直接通过类名来访问它。静态变量在内存中只存在一份;(2)静态方法:静态方法在类加载的时候就存在了,它不依赖于任何实例。所以静态方法必须有实现,也就是说它不能是抽象方法。只能访问所属类的静态字段和静态方法,方法中不能有 this 和 super 关键字;(3)静态语句块:静态语句块在类初始化时运行一次;(4)静态内部类:非静态内部类依赖于外部类的实例,而静态内部类不需要。静态内部类不能访问外部类的非静态的变量和方法;
(5)初始化顺序:静态变量和静态语句块优先于实例变量和普通语句块,静态变量和静态语句块的初始化顺序取决于它们在代码中的顺序。
21.super 关键字的作用?
(1)访问父类的构造函数:可以使用 super() 函数访问父类的构造函数,从而委托父类完成一些初始化的工作。(2)访问父类的成员:如果子类重写了父类的某个方法,可以通过使用 super 关键字来引用父类的方法实现。
(3)this 和 super 不能同时出现在一个构造函数里面,因为 this 必然会调用其它的构造函数,其它的构造函数必然也会有 super 语句的存在,所以在同一个构造函数里面有相同的语句,就失去了语句的意义,编译器也不会通过。
22.transient关键字的作用?
对于不想进行序列化的变量,使用 transient 关键字修饰。transient 关键字的作用是:阻止实例中那些用此关键字修饰的的变量序列化。当对象被反序列化时,被 transient 修饰的变量值不会被持久化和恢复。transient 只能修饰变量,不能修饰类和方法。
23.== 和 equals 的区别?
答:==:如果比较的对象是基本数据类型,则比较的是数值是否相等;如果比较的是引用数据类型,则比较的是对象的地址值是否相等。equals 方法:用来比较两个对象的内容是否相等。注意:equals 方法不能用于比较基本数据类型的变量。如果没有对 equals 方法进行重写,则比较的是引用类型的变量所指向的对象的地址(很多类重新了 equals 方法,比如 String、Integer 等把它变成了值比较,所以一般情况下 equals 比较的是值是否相等)。
24.两个对象的 hashCode() 相同,则 equals() 也一定为 true 吗?
答:两个对象的 hashCode() 相同,equals() 不一定为 true。因为在散列表中,hashCode() 相等即两个键值对的哈希值相等,然而哈希值相等,并不一定能得出键值对相等【散列冲突】。
25.为什么重写 equals() 就一定要重写 hashCode() 方法?
答:这个问题应该是有个前提,就是你需要用到 HashMap、HashSet 等 Java 集合,用不到哈希表的话,其实仅仅重写 equals() 方法也可以。而工作中的场景是常常用到 Java 集合,所以 Java 官方建议重写 equals() 就一定要重写 hashCode() 方法。
对于对象集合的判重,如果一个集合含有 10000 个对象实例,仅仅使用 equals() 方法的话,那么对于一个对象判重就需要比较 10000 次,随着集合规模的增大,时间开销是很大的。但是同时使用哈希表的话,就能快速定位到对象的大概存储位置,并且在定位到大概存储位置后,后续比较过程中,如果两个对象的 hashCode 不相同,也不再需要调用 equals() 方法,从而大大减少了 equals() 比较次数。
所以从程序实现原理上来讲的话,既需要 equals() 方法,也需要 hashCode() 方法。那么既然重写了 equals(),那么也要重写 hashCode() 方法,以保证两者之间的配合关系。
hashCode()与equals()的相关规定:
1、如果两个对象相等,则 hashCode 一定也是相同的;2、两个对象相等,对两个对象分别调用 equals 方法都返回 true;3、两个对象有相同的 hashCode 值,它们也不一定是相等的;4、因此,equals 方法被覆盖过,则 hashCode 方法也必须被覆盖;5、hashCode() 的默认行为是对堆上的对象产生独特值。如果没有重写 hashCode(),则该 class 的两个对象无论如何都不会相等(即使这两个对象指向相同的数据)。
26.& 和 && 的区别?
答:Java 中 && 和 & 都是表示与的逻辑运算符,都表示逻辑运输符 and,当两边的表达式都为 true 的时候,整个运算结果才为 true,否则为 false。
&&:有短路功能,当第一个表达式的值为 false 的时候,则不再计算第二个表达式;
&:不管第一个表达式结果是否为 true,第二个都会执行。除此之外,& 还可以用作位运算符:当 & 两边的表达式不是
27.Java 中的参数传递时传值呢?还是传引用?
答:Java 的参数是以值传递的形式传入方法中,而不是引用传递。当传递方法参数类型为基本数据类型(数字以及布尔值)时,一个方法是不可能修改一个基本数据类型的参数。当传递方法参数类型为引用数据类型时,一个方法将修改一个引用数据类型的参数所指向对象的值。即使 Java 函数在传递引用数据类型时,也只是拷贝了引用的值罢了,之所以能修改引用数据是因为它们同时指向了一个对象,但这仍然是按值调用而不是引用调用。
28.Java 中的 Math.round(-1.5) 等于多少?
答:等于 -1,因为在数轴上取值时,中间值(0.5)向右取整,所以正 0.5 是往上取整,负 0.5 是直接舍弃
29.两个二进制数的异或结果是什么?
答:两个二进制数异或结果是这两个二进制数差的绝对值。表达式如下:a^b = |a-b|。
两个二进制 a 与 b 异或,即 a 和 b 两个数按位进行运算。如果对应的位相同,则为 0(相当于对应的算术相减),如果不同即为 1(相当于对应的算术相加)。由于二进制每个位只有两种状态,要么是 0,要么是 1,则按位异或操作可表达为按位相减取值相对值,再按位累加。
30.Error 和 Exception 的区别?
答:Error 类和 Exception 类的父类都是 Throwable 类。主要区别如下:
Error 类: 一般是指与虚拟机相关的问题,如:系统崩溃、虚拟机错误、内存空间不足、方法调用栈溢出等。这类错误将会导致应用程序中断,仅靠程序本身无法恢复和预防;
Exception 类:分为运行时异常和受检查的异常。
31.运行时异常与受检异常有何异同?
答:运行时异常:如:空指针异常、指定的类找不到、数组越界、方法传递参数错误、数据类型转换错误。可以编译通过,但是一运行就停止了,程序不会自己处理;受检查异常:要么用 try … catch… 捕获,要么用 throws 声明抛出,交给父类处理。
32.throw 和 throws 的区别?
答:(1)throw:在方法体内部,表示抛出异常,由方法体内部的语句处理;throw 是具体向外抛出异常的动作,所以它抛出的是一个异常实例;(2)throws:在方法声明后面,表示如果抛出异常,由该方法的调用者来进行异常的处理;表示出现异常的可能性,并不一定会发生这种异常。
33.常见的异常类有哪些?
答:NullPointerException:当应用程序试图访问空对象时,则抛出该异常。SQLException:提供关于数据库访问错误或其他错误信息的异常。
IndexOutOfBoundsException:指示某排序索引(例如对数组、字符串或向量的排序)超出范围时抛出。
FileNotFoundException:当试图打开指定路径名表示的文件失败时,抛出此异常。
IOException:当发生某种 I/O 异常时,抛出此异常。此类是失败或中断的 I/O 操作生成的异常的通用类。
ClassCastException:当试图将对象强制转换为不是实例的子类时,抛出该异常。IllegalArgumentException:抛出的异常表明向方法传递了一个不合法或不正确的参数。
34.主线程可以捕获到子线程的异常吗?
答:线程设计的理念:“线程的问题应该线程自己本身来解决,而不要委托到外部”。
正常情况下,如果不做特殊的处理,在主线程中是不能够捕获到子线程中的异常的。如果想要在主线程中捕获子线程的异常,我们可以用如下的方式进行处理,使用 Thread 的静态方法。
Thread.setDefaultUncaughtExceptionHandler(new MyUncaughtExceptionHandle());
35.Java 的泛型是如何工作的 ? 什么是类型擦除 ?
答:泛型是通过类型擦除来实现的,编译器在编译时擦除了所有类型相关的信息,所以在运行时不存在任何类型相关的信息。例如:List 在运行时仅用一个 List 来表示。这样做的目的,是确保能和 Java 5 之前的版本开发二进制类库进行兼容。
类型擦除:泛型信息只存在于代码编译阶段,在进入 JVM 之前,与泛型相关的信息会被擦除掉,专业术语叫做类型擦除。在泛型类被类型擦除的时候,之前泛型类中的类型参数部分如果没有指定上限,如 则会被转译成普通的 Object 类型,如果指定了上限如 则类型参数就被替换成类型上限。
36.什么是泛型中的限定通配符和非限定通配符 ?
答:限定通配符对类型进行了限制。有两种限定通配符,一种是<? extends T> 它通过确保类型必须是 T 的子类来设定类型的上界,另一种是<? super T>它通过确保类型必须是 T 的父类来设定类型的下界。泛型类型必须用限定内的类型来进行初始化,否则会导致编译错误。另一方面 <?> 表示了非限定通配符,因为 <?> 可以用任意类型来替代。
37.如何实现对象的克隆?
答:(1)实现 Cloneable 接口并重写 Object 类中的 clone() 方法;(2)实现 Serializable 接口,通过对象的序列化和反序列化实现克隆,可以实现真正的深克隆。
38.深克隆和浅克隆的区别?
答:(1)浅克隆:拷贝对象和原始对象的引用类型引用同一个对象。浅克隆只是复制了对象的引用地址,两个对象指向同一个内存地址,所以修改其中任意的值,另一个值都会随之变化,这就是浅克隆。(2)深克隆:拷贝对象和原始对象的引用类型引用不同对象。深拷贝是将对象及值复制过来,两个对象修改其中任意的值另一个值不会改变,这就是深拷贝(例:JSON.parse() 和 JSON.stringify(),但是此方法无法复制函数类型)。
克隆的补充:
深克隆的实现就是在引用类型所在的类实现 Cloneable 接口,并使用 public 访问修饰符重写 clone 方法。Java 中定义的 clone 没有深浅之分,都是统一的调用 Object 的 clone 方法。为什么会有深克隆的概念?是由于我们在实现的过程中刻意的嵌套了 clone 方法的调用。也就是说深克隆就是在需要克隆的对象类型的类中重新实现克隆方法 clone()。
39.静态变量和实例变量的区别?
答:静态变量:是被 static 修饰的变量,也称为类变量,它属于类,因此不管创建多少个对象,静态变量在内存中有且仅有一个拷贝;静态变量可以实现让多个对象共享内存。实例变量:属于某一实例,需要先创建对象,然后通过对象才能访问到它。
40.抽象类和接口有什么区别?
答:(1)抽象类中可以定义构造函数,接口不能定义构造函数;(2)抽象类中可以有抽象方法和具体方法,而接口中只能有抽象方法(public abstract);(3)抽象类中的成员权限可以是 public、默认、protected(抽象类中抽象方法就是为了重写,所以不能被 private 修饰),而接口中的成员只可以是 public(方法默认:public abstrat、成员变量默认:public static final);(4)抽象类中可以包含静态方法,而接口中不可以包含静态方法;
JDK8中的改变:
1、在 JDK1.8中,允许在接口中包含带有具体实现的方法,使用 default 修饰,这类方法就是默认方法。
2、抽象类中可以包含静态方法,在 JDK1.8 之前接口中不能包含静态方法,JDK1.8 以后可以包含。之前不能包含是因为,接口不可以实现方法,只可以定义方法,所以不能使用静态方法(因为静态方法必须实现)。现在可以包含了,只能直接用接口调用静态方法。JDK1.8 仍然不可以包含静态代码块。
41.Java 中创建对象的几种方式?
答:1、使用 new 关键字;2、使用 Class 类的 newInstance 方法,该方法调用无参的构造器创建对象(反射):Class.forName.newInstance();3、使用 clone() 方法;4、反序列化,比如调用 ObjectInputStream 类的 readObject() 方法。
42.在 Java 中定义一个不做事且没有参数的构造方法有什么作用?
答:Java 程序在执行子类的构造方法之前,如果没有用 super() 来调用父类特定的构造方法,则会调用父类中“没有参数的构造方法”。因此,如果父类中只定义了有参数的构造方法,而在子类的构造方法中又没有用 super() 来调用父类中特定的构造方法,则编译时将发生错误,因为 Java 程序在父类中找不到没有参数的构造方法可供执行。解决办法是:在父类里加上一个不做事且没有参数的构造方法。
43.构造方法有哪些特性?
答:(1)名字与类名相同;
(2)没有返回值,但不能用 void 声明构造函数;
(3)成类的对象时自动执行,无需调用。
44.构造器是否可以被重写?
答:在讲继承的时候我们就知道父类的私有属性和构造方法并不能被继承,所以 Constructor 也就不能被 Override(重写),但是可以 Overload(重载),所以你可以看到一个类中有多个构造函数的情况。
45.Java 中是否可以重写一个 private 或者 static 方法?
答:Java 中 static 方法不能被覆盖,因为方法覆盖是基于运行时动态绑定的,而 static 方法是编译时静态绑定的。static 方法跟类的任何实例都不相关,所以概念上不适用。 Java 中也不可以覆盖 private 的方法,因为 private 修饰的变量和方法只能在当前类中使用, 如果是其他的类继承当前类是不能访问到 private 变量或方法的,当然也不能覆盖。
静态方法的补充
静态的方法可以被继承,但是不能重写。如果父类和子类中存在同样名称和参数的静态方法,那么该子类的方法会把原来继承过来的父类的方法隐藏,而不是重写。通俗的讲就是父类的方法和子类的方法是两个没有关系的方法,具体调用哪一个方法是看是哪个对象的引用;这种父子类方法也不在存在多态的性质。
46.重载和重写的区别?
答:(1)重载:编译时多态、同一个类中同名的方法具有不同的参数列表、不能根据返回类型进行区分【因为:函数调用时不能指定类型信息,编译器不知道你要调哪个函数】;(2)重写(又名覆盖):运行时多态、子类与父类之间、子类重写父类的方法具有相同的返回类型、更好的访问权限。
47.JDK、JRE、JVM 三者之间的关系?
答:JDK(Java Development Kit):是 Java 开发工具包,是整个 Java 的核心,包括了 Java 运行环境 JRE、Java 工具和 Java 基础类库。
JRE( Java Runtime Environment):是 Java 的运行环境,包含 JVM 标准实现及 Java 核心类库。
JVM(Java Virtual Machine):是 Java 虚拟机,是整个 Java 实现跨平台的最核心的部分,能够运行以 Java 语言写作的软件程序。所有的 Java 程序会首先被编译为 .class 的类文件,这种类文件可以在虚拟机上执行。
48.面向对象的三大特性?分别解释下?
答:(1)封装:通常认为封装是把数据和操作数据的方法封装起来,对数据的访问只能通过已定义的接口。(2)继承:继承是从已有类得到继承信息创建新类的过程。提供继承信息的类被称为父类(超类/基类),得到继承信息的被称为子类(派生类)。(3)多态:分为编译时多态(方法重载)和运行时多态(方法重写)。要实现多态需要做两件事:一是子类继承父类并重写父类中的方法,二是用父类型引用子类型对象,这样同样的引用调用同样的方法就会根据子类对象的不同而表现出不同的行为。
49.解释下什么是面向对象?面向对象和面向过程的区别?
答:面向对象是一种基于面向过程的编程思想,是向现实世界模型的自然延伸,这是一种“万物皆对象”的编程思想。由执行者变为指挥者,在现实生活中的任何物体都可以归为一类事物,而每一个个体都是一类事物的实例。面向对象的编程是以对象为中心,以消息为驱动。
区别: (1)编程思路不同:面向过程以实现功能的函数开发为主,而面向对象要首先抽象出类、属性及其方法,然后通过实例化类、执行方法来完成功能。 (2)封装性:都具有封装性,但是面向过程是封装的是功能,而面向对象封装的是数据和功能。 (3)面向对象具有继承性和多态性,而面向过程没有继承性和多态性,所以面向对象优势很明显。