每日十个面试题--(java基础篇)-(31-40)

Posted 江西昊仔

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了每日十个面试题--(java基础篇)-(31-40)相关的知识,希望对你有一定的参考价值。

每天更新,记得关注收藏哦!督促自己每天都了解一点点,一起加油。

题目内容

31、String s = new String(“xyz”); 创建了几个String Object?是否可以继承String类?
32、String、StringBuffer、StringBuilder它们的区别
33、下面这条语句一共创建了多少个对象:String s=“a”+“b”+“c”+“d”;
34、try {}里有一个return语句,那么紧跟在这个try后的finally{}里的code会不会被执行,什么时候被执行,在return前还是后?
35、final, finally, finalize的区别。
36、运行时异常与一般异常有何异同?
37、error和exception有什么区别?
38、简单说说Java中的异常处理机制的简单原理和应用。
39、Java 中堆和栈有什么区别?
40、能将 int 强制转换为 byte 类型的变量吗

31、String s = new String(“xyz”); 创建了几个String Object?是否可以继承String类?

堆区、常量池

问题分析 : 考官主要是对jvm方面问题考察

两个或一个都有可能

1.两个对象,一个在堆区,一个在字符串池。一个是xyz, 一个是指向xyz的引用对象s

”xyz”对应一个对象,这个对象放在字符串常量缓冲区,常量”xyz”不管出现多少遍,都是缓冲区中的那一个。

new String每写一遍,就创建一个新的对象,它是使用常量”xyz”对象的内容来创建出一个新String对象。

2.一个对象,在堆区。如果以前就用过’xyz’,那么这里就不会创建”xyz”了,直接从缓冲区拿,这时创建了一个String Object;

至于String类是否继承,答案是否定的,因为String默认final修饰,是不可继承的。

32、String、StringBuffer、StringBuilder它们的区别

是否可修改、线程

String 是不可变的,而 StringBuilder 和 StringBuffer 是可变的。

StringBuilder是线程不安全的,而 StringBuffer,String 是线程安全的。

这个String类提供了数值不可改变的字符串,对 String对象进行操作,返回的是新的对象,

在使用 StringBuffer 类时,每次都会对 StringBuffer 对象本身进行操作,而不是生成新的对象,

33、下面这条语句一共创建了多少个对象:String s=“a”+“b”+“c”+“d”;

编译优化

一个对象。在字符串常量池。

对于如下代码:

String s1 = "a"; 
String s2 = s1 + "b"; 
String s3 = "a" + "b";
System.out.println(s2 == "ab"); // false
System.out.println(s3 == "ab"); // true
// 打印内存地址,不要打印HashCode,不然都是常量池中字符串的HashCod,所有都一样。
System.out.println(System.identityHashCode("ab"));  // 471910020
System.out.println(System.identityHashCode(s2));	// 471910020
System.out.println(System.identityHashCode(s3));	// 531885035

第一条语句打印的结果为false,
第二条语句打印的结果为true,

这说明javac编译可以对字符串常量直接相加的表达式进行优化,不必要等到运行期再去进行加法运算处理,而是在编译时去掉其中的加号, 直接将其编译成一个这些常量相连的结果。

题目中的第一行代码被编译器在编译时优化后,相当于直接定义了一个”abcd”的字符串,所以,上面的 代码应该只创建了一个String对象。写如下两行代码,

对于如下代码:

String s ="a" + "b" +"c" + "d"; 
System.out.println(s== "abcd");  // true
// 打印内存地址
System.out.println(System.identityHashCode("a" + "b" +"c" + "d"));	// 471910020
System.out.println(System.identityHashCode("abcd"));				// 471910020
System.out.println(System.identityHashCode(s));						// 471910020

最终打印的结果应该为true。

34、try {}里有一个return语句,那么紧跟在这个try后的finally{}里的code会不会被执行,什么时候被执行,在return前还是后?.

暂时保存

先预执行最先出现的return,保留返回结果。 如果后面还有return,则覆盖前面的保留结果。 如果没有return,则结果不变。

35、final, finally, finalize的区别。

它们没有任何联系,只是长得像而已。

final 用于声明属性,方法和类,分别表示属性不可变,方法不可覆盖,类不可继承。内部类要访问局部变量,局部变量必须定义成final类型。

finally是异常处理语句结构的一部分,表示总是执行。

finalize是Object类的一个方法,在垃圾收集器执行的时候会调用被回收对象的此方法,可以覆盖此方法提供垃圾收集时的其他资源回收,例如关闭文件等。但是JVM不保证此方法总被调用

36、运行时异常与一般异常有何异同?

编写时、编译时

异常表示程序运行过程中可能出现的非正常状态,

运行时异常 表示虚拟机的通常操作中可能遇到的异常,是一种常见运行错误。

java编译器要求方法必须声明抛出可能发生的非运行时异常,但是并不要求必须声明抛出未被捕获的运行时异常。

运行时异常是可能被程序员避免的异常。

与检查性异常相反,运行时异常可以在编译时被忽略。

37、error和exception有什么区别?

是否可解决

error 表示恢复不是不可能,但很困难的情况下的一种严重问题。比如说内存溢出。不可能指望程序能处理这样的情况。

exception表示一种设计或实现问题。也就是说,它表示如果程序运行正常,从不会发生的情况。

38、简单说说Java中的异常处理机制的简单原理和应用。

异常是指java程序运行时(非编译)所发生的非正常情况或错误,与现实生活中的事件很相似,现实生活中的事件可以包含事件发生的时间、地点、人物、情节等信息,可以用一个对象来表示,Java使用面向对象的方式来处理异常,它把程序中发生的每个异常也都分别封装到一个对象来表示的,该对象中包含有异常的信息。

Java对异常进行了分类,不同类型的异常分别用不同的Java类表示,所有异常的根类为 java.lang.Throwable,Throwable下面又派生了两个子类:【Error】和【Exception】,

【Error】表示应用程序本身无法克服和恢复的一种严重问题,程序只有奔溃了,例如,说内存溢出和线程死锁等系统问题。

【Exception】表示程序还能够克服和恢复的问题,其中又分为系统异常和普通异常:

【系统异常】是软件本身缺陷所导致的问题,也就是软件开发人员考虑不周所导致的问题,软件使用者无法克服和恢复这种问题,但在这种问题下还可以让软件系统继续运行或者让软件挂掉,例如,数组下标越界(ArrayIndexOutOfBoundsException),空指针异常(NullPointerException)、类转换异常(ClassCastException);

【普通异常】是运行环境的变化或异常所导致的问题,是用户能够克服的问题,例如,网络断线,硬盘空间不够,发生这样的异常后,程序不应该死掉。

java为系统异常和普通异常提供了不同的解决方案,编译器强制普通异常必须try…catch处理或用throws 声明继续抛给上层调用方法处理,所以【普通异常】也称为【checked异常】,而系统异常可以处理也可以不处理,所以,编译器不强制用try…catch处理或用throws声明,所以【系统异常】也称为【unchecked异常】。

39、Java 中堆和栈有什么区别?

JVM中【堆】和【栈】属于不同的内存区域,使用目的也不同。

栈常用于保存方法帧和局部变量,而对象总是在堆上分配。

栈通常都比堆小,也不会在多个线程之间共享,而堆被整个 JVM 的所有线程共享。

栈:在函数中定义的一些基本类型的变量和对象的引用变量都是在函数的栈内存中分配,当在一段代码块定义一个变量时,Java 就在栈中为这个变量分配内存空间,当超过变量的作用域后,Java 会自动释放掉为该变量分配的内存空间,该内存空间可以立即被另作它用。

堆:堆内存用来存放由 new 创建的对象和数组,在堆中分配的内存,由 Java 虚拟机的自动垃圾回收器来管理。在堆中产生了一个数组或者对象之后,还可以在栈中定义一个特殊的变量,让栈中的这个变量的取值等于数组或对象在堆内存中的首地址,栈中的这个变量就成了数组或对象的引用变量,以后就可以在程序中使用栈中的引用变量来访问堆中的数组或者对象,引用变量就相当于是为数组或者对象起的一个名称。

40、能将 int 强制转换为 byte 类型的变量吗?如果该值大于 byte类型的范围,将会出现什么现象?

我们可以做强制转换,但是 Java 中 int 是 32 位的,而 byte 是 8 位的;

所以,如果强制转化,int 类 型的高 24 位将会被丢弃,因为byte 类型的范围是从 -128 到 127。

以上是关于每日十个面试题--(java基础篇)-(31-40)的主要内容,如果未能解决你的问题,请参考以下文章

每日十个面试题--(java基础篇)-(21-30)

每日十个面试题--(java基础篇)-(41-50)

每日十个面试题--(java基础篇)-(11-20)

每日十个面试题--(java基础篇)-(91-100)

每日十个面试题--(java基础篇)-(1-10)

每日十个面试题--(java基础篇)-(71-80)