专业的JAVA编程教程与资源

网站首页 > java教程 正文

「BAT常问」40道Java基础面试题及详细答案整理汇总「1—8」

temp10 2024-09-21 03:54:48 java教程 9 ℃ 0 评论

更多技术分享,请点击右上角红色的"关注",感谢你的支持!

本文接上篇,「BAT常问」40道Java基础面试题及详细答案整理汇总「开篇」,只是给大家一个提醒引入,将40道题目题干罗列供大家先自学,接下来的后续文章将把前文的题目一一解答,答案其实也都来自于网上,这里只是进行一些归纳整理和总结。40道题目都是比较高频的基础面试题,并不能囊括所有的面试重点,其他的更多面试题目要靠小伙伴们自己努力去搜集,并将之攻克了。

「BAT常问」40道Java基础面试题及详细答案整理汇总「1—8」

1.Java的基本数据类型几个,都是什么以及大小,以及他们的封装类有哪些?


8种基本数据类型:int、short、float、double、long、boolean、byte、char。

封装类型对应为:Integer、Short、Float、Double、Long、Boolean、Byte、Character。

2.什么是引用数据类型?


引用数据类型,是由类的编译器定义的,用于访问对象。这些变量被定义为不可更改的特定类型。

当一个变量值为引用类型的时候,直接赋值其他变量传递的是引用。

同样的,引用的数据在某个地方改变了值会影响所有调用这个变量的地方。

例如:Employee, Puppy 等等

  • 类对象和数组变量就是这种引用数据类型。

  • 任何引用数据类型的默认值都为null。

  • 一个引用数据类型可以被用于任何声明类型和兼容类型的对象。

3.条件语句中switch句柄,能否用string做为参数?


在jdk1.7之前,switch 只能支持 byte、short、char、int 这几个基本数据类型和其对应的封装类型。

switch后面的括号里面只能放int类型的值,但由于byte,short,char类型,它们会自动转换为int类型(精度小的向大的转化),所以这些现在都支持了

例如,

jdk1.7后,整型(int),枚举类,字符串(string)都可以支持

有个疑问,jdk1.7后又可以用string类型作为switch参数呢?

本质上是,jdk1.7并没有新的指令来处理switch string,而是通过调用switch中string.hashCode,将string转换为int从而进行判断。

4.equals与==的区别是什么?


使用==比较基本数据类型如:boolean、int、char等等,equals()用来比较对象是否为同一个。

1、==是判断两个变量或实例是不是指向同一个内存空间;

equals是判断两个变量或实例所指向的内存空间的值是不是相同。

2、==是指对内存地址进行比较;equals()是对字符串的内容进行比较。

3、==指引用是否相同; equals()指的是值是否相同。

直接看代码更清晰:

5.什么是自动装箱?常量池又是什么?


自动装箱 在jdk1.5之前,如果你想要定义一个value为100的Integer对象,则需要如下定义:

上面的代码中,intNum2为一个Integer类型的实例,intNum1为Java中的基础数据类型,将intNum1赋值给intNum2的过程就是自动装箱;而将intNum2赋值给intNum3得过程则是自动拆箱。这是一个相反的过程。

8种基本数据类型: boolean byte char shrot int long float double ,所生成的变量相当于常量。

对应的基本类型包装类:Boolean Byte Character Short Integer Long Float Double。

自动拆箱和自动装箱定义:

自动装箱是将一个java定义的基本数据类型赋值给相应封装类的变量。拆箱与装箱是相反的操作,自动拆箱则是将一个封装类的变量赋值给相应基本数据类型的变量。

6.Object都有什么公用的方法?

Object是所有类的父类,任何类都默认继承Object

clone方法,实现对象的浅复制,当实现了Cloneable接口才可以调用该方法,否则会抛出异常,类型为CloneNotSupportedException。

equals在Object中与==是一样的,子类一般需要重写该方法。

hashCode该方法用于哈希查找,重写了equals方法一般都要重写hashCode方法。这个方法在一些具有哈希功能的Collection中用到。

getClassfinal方法,获得运行时类型

wait使当前线程等待该对象的锁,当前线程必须是该对象的拥有者,也就是具有该对象的锁。wait() 方法一直等待,直到获得锁或者被中断。wait(long timeout) 设定一个超时间隔,如果在规定时间内没有获得锁就返回。

调用该方法后当前线程进入睡眠状态,直到以下事件发生

1、其他线程调用了该对象的notify方法。

2、其他线程调用了该对象的notifyAll方法。

3、其他线程调用了interrupt中断该线程。

4、时间间隔到了。

5、此时该线程就可以被调度了,如果是被中断的话就抛出一个InterruptedException异常。

notify唤醒在该对象上等待的某个线程。

notifyAll唤醒在该对象上等待的所有线程。

toString转换成字符串,一般子类都有重写,否则打印句柄。

7.Java的四种级别的引用都有什么?以及对应的引用场景在哪里?


从JDK1.2版本开始,把对象的引用分为四种级别,从而使程序能更加灵活的控制对象的生命周期。这四种级别由高到低依次为:强引用、软引用、弱引用和虚引用。

1、强引用

最普遍的一种引用方式,如String s = "abc",变量s就是字符串“abc”的强引用,只要强引用存在,则垃圾回收器就不会回收这个对象。

2、软引用(SoftReference)

用于描述还有用但非必须的对象,如果内存足够,不回收,如果内存不足,则回收。一般用于实现内存敏感的高速缓存,软引用可以和引用队列ReferenceQueue联合使用,如果软引用的对象被垃圾回收,JVM就会把这个软引用加入到与之关联的引用队列中。

3、弱引用(WeakReference)

弱引用和软引用大致相同,弱引用与软引用的区别在于:只具有弱引用的对象拥有更短暂的生命周期。在垃圾回收器线程扫描它所管辖的内存区域的过程中,一旦发现了只具有弱引用的对象,不管当前内存空间足够与否,都会回收它的内存。

4、虚引用(PhantomReference)

就是形同虚设,与其他几种引用都不同,虚引用并不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收。 虚引用主要用来跟踪对象被垃圾回收器回收的活动。

虚引用与软引用和弱引用的一个区别在于:

虚引用必须和引用队列 (ReferenceQueue)联合使用。当垃圾回收器准备回收一个对象时,如果发现它还有虚引,就会在回收对象的内存之前,把这个虚引用加入到与之关联的引用队列中。

8.Java中Hashcode的作用是什么?


1、HashCode的特性

(1)HashCode的存在主要是用于查找的快捷性,如Hashtable,HashMap等,HashCode经常用于确定对象的存储地址

(2)如果两个对象相同,equals方法一定返回true,并且这两个对象的HashCode一定相同

(3)两个对象的HashCode相同,并不一定表示两个对象就相同,即equals()不一定为true,只能够说明这两个对象在一个散列存储结构中。

(4)如果对象的equals方法被重写,那么对象的HashCode也应该重写

2、HashCode作用

Java中的集合有两类,一类是List,再有一类是Set。前者集合内的元素是有序的,元素可以重复;后者元素无序,但元素不可重复

equals方法可用于保证元素不重复,但如果每增加一个元素就检查一次,若集合中现在已经有1000个元素,那么第1001个元素加入集合时,就要调用1000次equals方法。这显然会大大降低效率。?于是,Java采用了哈希表的原理

哈希算法也称为散列算法,是将数据依特定算法直接指定到一个地址上。

这样一来,当集合要添加新的元素时,先调用这个元素的HashCode方法,就一下子能定位到它应该放置的物理位置上

(1)如果这个位置上没有元素,它就可以直接存储在这个位置上,不用再进行任何比较了。

(2)如果这个位置上已经有元素了,就调用它的equals方法与新元素进行比较,相同的话就不存了。

(3)不相同的话,也就是发生了Hash key相同导致冲突的情况,那么就在这个Hash key的地方产生一个链表,将所有产生相同HashCode的对象放到这个单链表上去,串在一起(很少出现)。

这样一来实际调用equals方法的次数就大大降低了,几乎只需要一两次。

如何理解HashCode的作用:

从Object角度看,JVM每new一个Object,它都会将这个Object丢到一个Hash表中去,这样的话,下次做Object的比较或者取这个对象的时候(读取过程),它会根据对象的HashCode再从Hash表中取这个对象。这样做的目的是提高取对象的效率。若HashCode相同再去调用equal。

3、HashCode实践(如何用来查找)

HashCode是用于查找使用的,而equals是用于比较两个对象是否相等的

(1)例如内存中有这样的位置

0 1 2 3 4 5 6 7

而我有个类,这个类有个字段叫ID,我要把这个类存放在以上8个位置之一,如果不用HashCode而任意存放,那么当查找时就需要到这八个位置里挨个去找,或者用二分法一类的算法。

但以上问题如果用HashCode就会使效率提高很多定义我们的HashCode为ID%8,比如我们的ID为9,9除8的余数为1,那么我们就把该类存在1这个位置,如果ID是13,求得的余数是5,那么我们就把该类放在5这个位置。依此类推。

(2)但是如果两个类有相同的HashCode,例如9除以8和17除以8的余数都是1,也就是说,我们先通过?HashCode来判断两个类是否存放某个桶里,但这个桶里可能有很多类,那么我们就需要再通过equals在这个桶里找到我们要的类

看一下下边的代码:

输出是:

true

false

[HashTest@1, HashTest@1]

以上这个示例,我们只是重写了HashCode方法,从上面的结果可以看出,虽然两个对象的HashCode相等,但是实际上两个对象并不是相等因为我们没有重写equals方法,那么就会调用Object默认的equals方法,显示这是两个不同的对象。

这里我们将生成的对象放到了HashSet中,而HashSet中只能够存放唯一的对象,也就是相同的(适用于equals方法)的对象只会存放一个,但是这里实际上是两个对象ab都被放到了HashSet中,这样HashSet就失去了他本身的意义了。

把equals方法重写如下:

输出如下:

true

true

[HashTest@1]

可以看到,两个对象已经完全相等了,在HashSet中也只存放了一份对象。

注意:hashCode()只是简单举例,实际的生产环境中一般不这样做

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表