Java基础(面试题)

1、final关键字的作用

2、abstract class和interface有什么区别?

3、Java集合类:List、set、queue、map、stack的特点与用法?

4、说出ArrayList、Vector、linkedList的存储性能和特性

5、内存泄露和内存溢出

6、反射中,Class,forName()和ClassLoader.loadClass()的区别?

7、int和integer的区别?

8、String、StringBuilder、StringBuffer的区别?

9、Hashtable和Hashmap的区别?

10、Error和Exception。

11、方法重载、方法重写

12、throw、throws

13、抽象类和接口区别

14、Java的基础类型和字节大小?

15、四个访问修饰符的访问等级?

16、HashSet的底层实现

17、抽象类的意义

18、重写equals的为什么要重写hashCode方法?

19、HashSet和TreeSet有什么区别?

20、强引用、软引用、弱引用、虚引用

21、数组在内存中如何分配

22、Java中如何创建一个不可变对象?

23、++操作符是线程安全的吗

24、new一个对象的过程和clone一个对象的过程?

25、==和equals

26、final、finalize、finnally

27、多态的表现

28、静态类型有什么特点?

29、Java创建对象的几种方式?

30、Object中有哪些公共方法?

31、&和&&的区别

32、在.java源文件中可以有多个类吗(内部类除外)

33、如何正确的退出多层嵌套循环?

34、内部类有什么作用?

35、深拷贝和浅拷贝的区别是什么?

36、String是基本数据类型吗

37、static的用法

38、什么是值传递和引用传递?

39、重载和重写的区别

40、成员变量和局部变量的区别有哪些?

41、静态方法和实例方法有何不同

42、什么是多态以及优点,多态存在的三个必要条件?

43、TreeMap、HashMap、LinedHashMap的区别

44、Java(OOP)面向对象的特征有哪些?

45、获取class的三种方式

46、break和continue的区别

47、Collection和Collections的区别

48、Comparable和Comparator接口的区别

49、switch能否作用在byte、long、string上?

50、jdk中有哪些类是不能继承的?

51、JDK与JRE的区别

52、是否可以在static环境中访问非static变量

53、Java支持多继承吗

54、什么是迭代器(Iterator)

55、Iterator和ListIterator的区别

56、Enumeration接口和Iterator接口的区别有哪些?

57、字符串常量池到底存在内存空间的哪里?

58、Java中的编译期常量是什么?使用它有什么风险?

59、用哪两种方式来实现集合的排序?

60、ArrayList源码分析

61、HashMap源码分析

62、ConcurrentHashMap源码分析

1、final 关键字的作用?

        被 final 修饰的类不可以被继承,被 final 修饰的方法不可以被重写,被 final 修饰的变量不可以被改变.如果修饰引用,那么表示引用不可变,引用指向的内容可变.被 final 修饰的方法,JVM 会尝试将其内联,以提高运行效率,被 final 修饰的常量,在编译阶段会存入常量池中。

2、abstract class 和 interface 有什么区别?

        声明方法的存在而不去实现它的类被叫做抽象类(abstract class),它用于要创建一个体现某些基本行为的类,并为该类声明方法,但不能在该类中实现该类的情况。不能创建abstract 类的实例。然而可以创建一个变量,其类型是一个抽象类,并让它指向具体子类的一个实例。不能有抽象构造函数或抽象静态方法。Abstract 类的子类为它们父类中的所有抽象方法提供实现,否则它们也是抽象类为。取而代之,在子类中实现该方法。知道其行为的其它类可以在类中实现这些方法。 接口(interface)是抽象类的变体。在接口中,所有方法都是抽象的。多继承性可通过实现这样的接口而获得。接口中的所有方法都是抽象的,没有一个有程序体。接口只可以定义static final 成员变量。接口的实现与子类相似,除了该实现类不能从接口定义中继承行为。当类实现特殊接口时,它定义(即将程序体给予)所有这种接口的方法。然后,它可以在实现了该接口的类的任何对象上调用接口的方法。由于有抽象类,它允许使用接口名作为引用变量的类型。通常的动态联编将生效。引用可以转换到接口类型或从接口类型转换,instanceof 运算符可以用来决定某对象的类是否实现了接口

3、Java 集合类:list、set、queue、map、stack 的特点与用法?

        Map Map 是键值对,键 Key 是唯一不能重复的,一个键对应一个值,值可以重复。 TreeMap 可以保证顺序,HashMap 不保证顺序,即为无序的,Map 中可以将 Key 和 Value 单 独抽取出来,其中 KeySet()方法可以将所有的 keys 抽取成一个 Set,而 Values()方法可以 将 map 中所有的 values 抽取成一个集合。 Set 不包含重复元素的集合,set 中最多包含一个 null 元素,只能用 Iterator 实现单项遍历, Set 中没有同步方法。 List 有序的可重复集合,可以在任意位置增加删除元素,用 Iterator 实现单向遍历,也可用 ListIterator 实现双向遍历。 Queue Queue 遵从先进先出原则,使用时尽量避免 add()和 remove()方法,而是使用 offer()来添加 元素,使用 poll()来移除元素,它的优点是可以通过返回值来判断是否成功,LinkedList 实现了 Queue 接口,Queue 通常不允许插入 null 元素。 Stack Stack 遵从后进先出原则,Stack 继承自 Vector,它通过五个操作对类 Vector 进行扩展, 允许将向量视为堆栈,它提供了通常的 push 和 pop 操作,以及取堆栈顶点的 peek()方法、测试堆栈是否为空的 empty 方法等。 用法 如果涉及堆栈,队列等操作,建议使用 List。 对于快速插入和删除元素的,建议使用 LinkedList。如果需要快速随机访问元素的,建议使用 ArrayList。

4、说出 ArrayList,Vector, LinkedList 的存储性能和特性?

        ArrayList 和 Vector 都是使用数组方式存储数据,此数组元素数大于实际存储的数据以便增加和插入元素,它们都允许直接按序号索引元素,但是插入元素要涉及数组元素移动等内存操作,所以索引数据快而插入数据慢,Vector 由于使用了 synchronized 方法(线程安全),通常性能上较 ArrayList 差,而 LinkedList 使用双向链表实现存储,按序号索引数据需要进行前向或后向遍历,但是插入数据时只需要记录本项的前后项即可,所以插入速度较快。

5、内存泄漏和内存溢出?

        内存泄漏(memoryleak),是指应用程序在申请内存后,无法释放已经申请的内存空间,一次内存泄漏危害可以忽略,但如果任其发展最终会导致内存溢出(outofmemory)。如读取文件后流要进行及时的关闭以及对数据库连接的释放。 内存溢出(outofmemory)是指应用程序在申请内存时,没有足够的内存空间供其使用。如我 们在项目中对于大批量数据的导入,采用分批量提交的方式。

6、反射中,Class.forName()和 ClassLoader.loadClass()的区别?

        Class.forName(className) 方 法 , 内 部 实 际 调 用 的 方 法 是 Class.forName(className,true,classloader); 第 2 个 boolean 参数表示类是否需要初始化, Class.forName(className)默认是需要初始化,一旦初始化,就会触发目标对象的 static 块代码执行,static 参数也也会被再次初始化 ,ClassLoader.loadClass(className) 方 法 , 内 部 实 际 调 用 的 方 法 是ClassLoader.loadClass(className,false);第 2 个 boolean 参数,表示目标对象是否进行链接,false 表示不进行链接,由上面介绍可以,不进行链接意味着不进行包括初始化等一些列步 骤,那么静态块和静态对象就不会得到执行

7、Int 和 Integer 的区别?

        Integer 是 int 的包装类型,在拆箱和装箱中,二者自动转换.int 是基本类型,直接存数值;而 integer 是对象;用一个引用指向这个对象.由于 Integer 是一个对象,在 JVM 中对象需要一定的数据结构进行描述,相比 int 而言,其占用的内存更大一些。

8、String、StringBuilder、StringBuffer 区别?

         String 字符串常量 不可变 使用字符串拼接时是不同的 2 个空间

         StringBuffer 字符串变量

         StringBuilder 字符串变量 可变可变 线程安全 字符串拼接直接在字符串后追加非线程安全 字符串拼接直接在字符串后追加

        1.StringBuilder 执行效率高于 StringBuffer 高于 String

        2.String 是一个常量,是不可变的,所以对于每一次+=赋值都会创建一个新的对象,StringBuffer 和 StringBuilder 都是可变的,当进行字符串拼接时采用 append 方 法,在原来的基础上进行追加,所以性能比 String 要高,又因为 StringBuffer 是 线程安全的而 StringBuilder 是线程非安全的,所以 StringBuilder 的效率高于StringBuffer.

        3.对于大数据量的字符串的拼接,采用 StringBuffer,StringBuilder.

9、Hashtable 和 Hashmap 的区别?

        1、HashTable 线程安全,HashMap 非线程安全

         2、Hashtable 不允许 null 值(key 和 value 都不可以),HashMap 允许 null 值(key 和value 都可以)。

        3、两者的遍历方式大同小异,Hashtable 仅仅比 HashMap 多一个 elements 方法。

10、说几个常见的编译时异常?

        SQLException 提供有关数据库访问错误或其他错误的信息的异常。IOexception 表示发生了某种 I / O 异常的信号。此类是由失败或中断的 I / O 操作产生的一般异常类 FileNotFoundException 当试图打开指定路径名表示的文件失败时,抛出此异常。ClassNotFoundException 找不到具有指定名称的类的定义。EOFException 当输入过程中意外到达文件或流的末尾时,抛出此异常。

11、方法重载的规则?

        方法名一致,参数列表中参数的顺序,类型,个数不同。重载与方法的返回值无关,存在于父类和子类,同类中。可以抛出不同的异常,可以有不同修饰符。

12、方法重写的规则?

        参数列表、方法名、返回值类型必须完全一致,构造方法不能被重写;声明为 final 的方法不能被重写;声明为 static 的方法不存在重写(重写和多态联合才有意义);访问权限不能比父类更低;重写之后的方法不能抛出更宽泛的异常

13、throw 和 throws 的区别?

        throw: throw 语句用在方法体内,表示抛出异常,由方法体内的语句处理。throw 是具体向外抛出异常的动作,所以它抛出的是一个异常实例,执行 throw 一定是抛出了某种异常。

        throws: throws 语句是用在方法声明后面,表示如果抛出异常,由该方法的调用者来进行异常的处理。throws 主要是声明这个方法会抛出某种类型的异常,让它的使用者要知道需要捕获的异常的类型。throws 表示出现异常的一种可能性,并不一定会发生这种异常。

14、抽象类和接口的区别?

        1、接口中所有的方法隐含的都是抽象的。而抽象类则可以同时包含抽象和非抽象的方法。        

        2、类可以实现很多个接口,但是只能继承一个抽象类

        3、类如果要实现一个接口,它必须要实现接口声明的所有方法。但是,类可以不实现抽象类声明的所有方法,当然,在这种情况下,类也必须得声明成是抽象的。

        4、抽象类可以在不提供接口方法实现的情况下实现接口。

        5、Java 接口中声明的变量默认都是 final 的。抽象类可以包含非 final 的变量。

        6、Java 接口中的成员函数默认是 public 的。抽象类的成员函数可以是 private,protecte或者是 public 。

        7、接口是绝对抽象的,不可以被实例化(java 8 已支持在接口中实现默认的方法)。抽象类也不可以被实例化,但是,如果它包含 main 方法的话是可以被调用的。

15、Java 的基础类型和字节大小?

        布尔型 boolean 8 位;字节型 byte 8 位; 字符型 char 16 位;短整型 short 16 位;整形 int 32 位; 长整形 long 64 位;浮点型 float 32 位;双精度 double 64 位;

16、String 和 StringBuffer 的区别?

        String 和 StringBuffer 主要区别是性能:String 是不可变对象,每次对 String 类型进行操作都等同于产生了一个新的 String 对象,然后指向新的 String 对象.所以尽量不要对String 进行大量的拼接操作,否则会产生很多临时对象,导致 GC 开始工作,影响系统性能.StringBuffer 是对象本身操作,而不是产生新的对象,因此在有大量拼接的情况下,我们建议使用 StringBuffer(线程安全).

17、HashSet 的底层实现是什么?

        HashSet 的实现是依赖于 HashMap 的,HashSet 的值都是存储在 HashMap 中的。在 HashSet 的构造法中会初始化一个 HashMap 对象,HashSet 不允许值重复。因此,HashSet 的值是作为 HashMap 的 key 存储在 HashMap 中的,当存储的值已经存在时返回 false。

18、抽象类的意义?

        抽象类的意义可以用三句话来概括:1、为其他子类提供一个公共的类型2、封装子类中重复定义的内容 千锋成都 Java 教学部 3、定义抽象方法,子类虽然有不同的实现,但是定义时一致的

19、 你为什么重写 equals 时必须重写 hashCode 方法?

         hashCode() 的作用是获取哈希码,也称为散列码;它实际上是返回一个 int 整数。这个哈希码的作用是确定该对象在哈希表中的索引位置。如果两个对象相等,则 hashcode 一定也是相同的如果两个对象相等,对两个对象分别调用 equals 方法都返回 true 如果两个对象有相同的 hashcode 值,它们也不一定是相等的因此,equals 方法被覆盖过,则 hashCode 方法也必须被覆盖。 hashCode()的默认行为是对堆上的对象产生独特值。如果没有重写 hashCode(),则该 class的两个对象无论如何都不会相等(即使这两个对象指向相同的数据).

20、HashSet 和 TreeSet 有什么区别?

         HashSet 是由一个 hash 表来实现的,因此,它的元素是无序的。add(),remove(),contains()方法的时间复杂度是 O(1)。TreeSet 是由一个树形的结构来实现的,它里面的元素是有序的。因此,add(),remove(),contains()方法的时间复杂度是 O(logn)。

21、强引用和软引用和弱引用以及虚引用?

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

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

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

        4、虚引用(PhantomReference) 就是形同虚设,与其他几种引用都不同,虚引用并不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收。 虚引用主要用来跟踪对象被垃圾回收器回收的活动。 虚引用与软引用和弱引用的一个区别在于: 虚引用必须和引用队列 (ReferenceQueue)联合使用。当垃圾回收器准备回收一个对象时,如果发现它还有虚引,就会在回收对象的内存之前,把这个虚引用加入到与之关联的引用队列中。

22、 数组在内存中如何分配?

        当一个对象使用 new 关键字创建的时候,会在堆上分配内存空间,然后才返回到对象的引用。这对数组来说也是一样的,因为数组也是一个对象,简单的值类型的数组,每个数组成员是一个引用(指针)引用到栈上的空间。 

23、 Java 中怎么创建一个不可变对象?

        1. 对象的状态在构造函数之后都不能被修改,任何修改应该通过创建一个新对象来实现.

        2. 所有的对象属性应该都设置为 final

        3. 对象创建要正确,例如:对象的应用不能在构造函数中被泄露出去

        4. 对象要设置为 final,确保不要继承的 Class 修改了 immutability 特性

24、 Java 中 ++ 操作符是线程安全的吗?

        不是线程安全的操作。它涉及到多个指令,如读取变量值,增加,然后存储回内存,这个过程可能会出现多个线程交差。

25、new 一个对象的过程和 clone 一个对象的过程?

        new 操作符的本意是分配内存。程序执行到 new 操作符时,首先去看 new 操作符后面的类型,因为知道了类型,才能知道要分配多大的内存空间。分配完内存之后,再调用构造函数,填充对象的各个域,这一步叫做对象的初始化,构造方法返回后,一个对象创建完毕,可以把他的引用(地址)发布到外部,在外部就可以使用这个引用操纵这个对象。clone 在第一步是和 new 相似的,都是分配内存,调用 clone 方法时,分配的内存和原对象(即调用 clone 方法的对象)相同,然后再使用原对象中对应的各个域,填充新对象的域,填充完成之后,clone 方法返回,一个新的相同的对象被创建,同样可以把这个新对象的引用发布到外部。

26、Java 中==和 equals()的区别?

         使用==比较原生类型如:boolean、int、char 等等,使用 equals()比较对象。1、==是判断两个变量或实例是不是指向同一个内存空间。equals 是判断两个变量或实例所指向的内存空间的值是不是相同。 2、==是指对内存地址进行比较。equals()是对字符串的内容进行比较。3、==指引用是否相同,equals()指的是值是否相同。

27、 final、finalize 和 finally 的不同之处?

        final 用于声明属性,方法和类,分别表示属性不可变,方法不可覆盖,类不可继承。finally 是异常处理语句结构的一部分,表示总是执行。 finalize 是 Object 类的一个方法,在垃圾收集器执行的时候会调用被回收对象的此方法,可以覆盖此方法提供垃圾收集时的其他资源回收,例如关闭文件等。

28、Java 的多态表现在哪里?

         多态要有动态绑定,否则就不是多态,方法重载也不是多态(因为方法重载是编译期决定好的,没有后期也就是运行期的动态绑定)当满足这三个条件:1、有继承 2、有重写 3、要有父类引用指向子类对象

29、静态类型有什么特点?

         1、静态的属性:随着类的加载而加载,该属性不在属于某个对象,属于整个类 2、静态的方法:直接用类名调用,静态方法里不能访问非静态成员变量3、静态类:不能直接创建对象,不可被继承

30、Java 创建对象的几种方式?

        new 创建新对象;通过反射机制;采用 clone 机制;通过序列化机制

31、Object 中有哪些公共方法?

        Object 是所有类的父类,任何类都默认继承 Object clone 保护方法,实现对象的浅复制,只有实现了 Cloneable 接口才可以调用该方法,否则抛出 CloneNotSupportedException 异常。equals 在 Object 中与==是一样的,子类一般需要重写该方法。hashCode 该方法用于哈希查找,重写了 equals 方法一般都要重写 hashCode 方法。这个方法在一些具有哈希功能的Collection 中用到。getClass final 方法,获得运行时类型 wait 使当前线程等待该对象的锁,当前线程必须是该对象的拥有者,也就是具有该对象的锁。wait()方法一直等待,直到获得锁或者被中断。wait(long timeout)设定一个超时间隔,如果在规定时间内没有获得锁就返回。

32、&和&&的区别?

        &是位运算符,表示按位与运算,&&是逻辑运算符,表示逻辑与(and)。

33、在.java 源文件中可以有多个类吗(内部类除外)?

        一个.java 源文件中可以包括多个类(不是内部类),但是单个文件中只能有一个 public类,并且该 public 类必须与文件名相同

34、如何正确的退出多层嵌套循环?

         1、使用标号和 break; 2、通过在外层循环中添加标识符

35、内部类有什么作用?

         1、内部类可以很好的实现隐藏,一般的非内部类,是不允许有 private 与 protected权限的,但内部类可以

        2、内部类拥有外围类的所有元素的访问权限

        3、可是实现多重继承

        4、可以避免修改接口而实现同一个类中两种同名方法的调用

36、深拷贝和浅拷贝的区别是什么?

        浅拷贝:被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用仍然指向原来的对象.换言之,浅拷贝仅仅复制所考虑的对象,而不复制它所引用的对象.

        深拷贝:被复制对象的所有变量都含有与原来的对象相同的值.而那些引用其他对象的变量将指向被复制过的新对象.而不再是原有的那些被引用的对象.换言之.深拷贝把要复制的对象所引用的对象都复制了一遍.

37、static 的用法?

        Static 可以修饰内部类、方法、变量、代码块;Static 修饰的类是静态内部类;Static 修饰的方法是静态方法,表示该方法属于当前类的,而不属于某个对象的,静态方法也不能被重写,可以直接使用类名来调用。在 static 方法中不能使用 this 或者 super 关键字。Static 修饰变量是静态变量或者叫类变量,静态变量被所有实例所共享,不会依赖于对象。静态变量在内存中只有一份拷贝,在 JVM 加载类的时候,只为静态分配一次内存。Static 修饰的代码块叫静态代码块,通常用来做程序优化的。静态代码块中的代码在整个类加载的时候只会执行一次。静态代码块可以有多个,如果有多个,按照先后顺序依次执行。

40、什么是值传递和引用传递?

        对象被值传递,意味着传递了对象的一个副本。因此,就算是改变了对象副本,也不会影响源对象的值,对象被引用传递,意味着传递的并不是实际的对象,而是对象的引用。因此,外部对引用对象所做的改变会反映到所有的对象上。

41、重载和重写的区别?

        方法的重写 Overriding 和重载 Overloading 是 Java 多态性的不同表现。重写 Overriding是父类与子类之间多态性的一种表现,重载 Overloading 是一个类中多态性的一种表现。如果在子类中定义某方法与其父类有相同的名称和参数,我们说该方法被重写 (Overriding)。子类的对象使用这个方法时,将调用子类中的定义,对它而言,父类中的定义如同被“屏蔽”了。如果在一个类中定义了多个同名的方法,它们或有不同的参数个数或有不同的参数类型,则称为方法的重载(Overloading)。

42、员变量和局部变量的区别有哪些?

        1、从语法形式上,看成员变量是属于类的,而局部变量是在方法中定义的变量或是方法的参数;成员变量可以被 public,private,static 等修饰符所修饰,而局部变量不能被访问控制修饰符及 static 所修饰;成员变量和局部变量都能被 final 所修饰;

        2、从变量在内存中的存储方式来看,成员变量是对象的一部分,而对象存在于堆内存,局部变量存在于栈内存

        3、从变量在内存中的生存时间上看,成员变量是对象的一部分,它随着对象的创建而存在,而局部变量随着方法的调用而自动消失。

        4、成员变量如果没有被赋初值,则会自动以类型的默认值而赋值(一种情况例外被 final修饰但没有被 static 修饰的成员变量必须显示地赋值);而局部变量则不会自动赋值。

43、静态方法和实例方法有何不同?

        静态方法和实例方法的区别主要体现在两个方面: 在外部调用静态方法时,可以使用"类名.方法名"的方式,也可以使用"对象名.方法名"的方式。而实例方法只有后面这种方式。也就是说,调用静态方法可以无需创建对象。静态方法在访问本类的成员时,只允许访问静态成员(即静态成员变量和静态方法),而不允许访问实例成员变量和实例方法;实例方法则无此限制

44、什么是多态?

        允许不同类的对象对同一消息做出响应。即同一消息可以根据发送对象的不同而采用多种不同的行为方式。(发送消息就是函数调用)

45、多态的优点?

        可替换性(substitutability)。多态对已存在代码具有可替换性。例如,多态对圆 Circle类工作,对其他任何圆形几何体,如圆环,也同样工作。 可扩充性(extensibility)。多态对代码具有可扩充性。增加新的子类不影响已存在类的多态性、继承性,以及其他特性的运行和操作。实际上新加子类更容易获得多态功能。

46、多态存在的三个必要条件?

         要有继承。 要有方法的重写。 父类引用指向子类对象(对于父类中定义的方法,如果子类中重写了该方法,那么父类类型的引用将会调用子类中的这个方法,这就是动态连接)

47. TreeMap、HashMap、LindedHashMap 的区别?

         LinkedHashMap 可以保证 HashMap 集合有序。存入的顺序和取出的顺序一致。TreeMap 实现SortMap 接口,能够把它保存的记录根据键排序,默认是按键值的升序排序,也可以指定排序的比较器,当用 Iterator 遍历 TreeMap 时,得到的记录是排过序的。HashMap 不保证顺序,即为无序的,具有很快的访问速度。HashMap 最多只允许一条记录的键为 Null;允许多条记录的值为 Null;HashMap 不支持线程的同步。

48.Java(OOP)面向对象的特征有哪些方面?

        1)抽象:抽象是将一类对象的共同特征总结出来构造类的过程,包括数据抽象和行为抽象两方面。抽象只关注对象有哪些属性和行为,并不关注这些行为的细节是什么。

        2)继承:继承是从已有类得到继承信息创建新类的过程。提供继承信息的类被称为父类(超类、基类);得到继承信息的类被称为子类(派生类)。继承让变化中的软件系统有了一定的延续性,同时继承也是封装程序中可变因素的重要手段。

        3)封装:通常认为封装是把数据和操作数据的方法绑定起来,对数据的访问只能通过已定义的接口。面向对象的本质就是将现实世界描绘成一系列完全自治、封闭的对象。我们在类中编写的方法就是对实现细节的一种封装;我们编写一个类就是对数据和数据操作的封装。可以说,封装就是隐藏一切可隐藏的东西,只向外界提供最简单的编程接口。 4)多态性:多态性是指允许不同子类型的对象对同一消息作出不同的响应。简单的说就是用同样的对象引用调用同样的方法但是做了不同的事情。多态性分为编译时的多态性和运行时的多态性。如果将对象的方法视为对象向外界提供的服务,那么运行时的多态性可以解释为:当 A 系统访问 B 系统提供的服务时,B 系统有多种提供服务的方式,但一切对 A 系统来说都是透明的。方法重载(overload)实现的是编译时的多态性(也称为前绑定),而方法重写(override)实现的是运行时的多态性(也称为后绑定)。运行时的多态是面向对象最精髓的东西,要实现多态需要做两件事:1. 方法重写(子类继承父类并重写父类中已有的或抽象的方法);2. 对象造型(用父类型引用引用子类型对象,这样同样的引用调用同样的方法就会根据子类对象的不同而表现出不同的行为)。

49、列出一些常见的运行时异常?

        ArithmeticException(算术异常) ClassCastException (类转换异常)IllegalArgumentException (非法参数异常)IndexOutOfBoundsException (下标越界异常)NullPointerException (空指针异常)SecurityException (安全异常)

50、什么是反射?

         反射就是动态加载对象,并对对象进行剖析。在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法,这种动态获取信息以及动态调用对象方法的功能成为 Java 反射机制。

51、反射的作用?

         1)在运行时判断任意一个对象所属的类

        2)在运行时构造任意一个类的对象

        3)在运行时判断任意一个类所具有的成员变量和方法

        4)在运行时调用任意一个对象的方法

52、获取 class 的三种方式?

        对象调用 getClass() 方法来获取;类名.class 的方式得到;通过 Class 对象的 forName()静态方法来获取

53、break 和 continue 的区别?

        break 和 continue 都是用来控制循环的语句。break 用于完全结束一个循环,跳出循环体执行循环后面的语句。continue 用于跳过本次循环,继续下次循环。 千锋成都 Java 教学部

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

        异常表示程序运行过程中可能出现的非正常状态,运行时异常表示虚拟机的通常操作中可能遇到的异常,是一种常见运行错误。java 编译器要求方法必须声明抛出可能发生的非运行时异常,但是并不要求必须声明抛出未被捕获的运行时异常。

55、List、Map、Set 三个接口存取元素时,各有什么特点?

        List 以特定索引来存取元素,可以有重复元素。Set 不能存放重复元素(用对象的 equals()方法来区分元素是否重复)。Map 保存键值对(key-value pair)映射,映射关系可以是一对一或多对一

56、Collection 和 Collections 的区别?

        Collection 是集合类的上级接口,继承与他的接口主要有 Set 和 List.Collections 是针对集合类的一个帮助类,他提供一系列静态方法实现对各种集合的搜索、排序、线程安全化等操作。

57、Error 和 Exception 有什么区别?

        error 表示恢复不是不可能但很困难的情况下的一种严重问题。比如说内存溢出。不可能指望程序能处理这样的情况。exception 表示一种设计或实现问题。也就是说,它表示如果程序运行正常,从不会发生的情况。 58、EJB 的生命周期,以及如何管理事务?

        SessionBean:Stateless Session Bean 的生命周期是由容器决定的,当客户机发出请求要建立一个 Bean 的实例时,EJB 容器不一定要创建一个新的 Bean 的实例供客户机调用,而是随便找一个现有的实例提供给客户机。当客户机第一次调用一个 Stateful Session Bean时,容器必须立即在服务器中创建一个新的 Bean 实例,并关联到客户机上,以后此客户机调用 Stateful Session Bean 的方法时容器会把调用分派到与此客户机相关联的 Bean 实例。EntityBean:Entity Beans 能存活相对较长的时间,并且状态是持续的。只要数据库中的数据存在,Entity beans 就一直存活。而不是按照应用程序或者服务进程来说的。即使 EJB容器崩溃了,Entity beans 也是存活的。Entity Beans 生命周期能够被容器或者 Beans 自己管理。EJB 通过以下技术管理实务:对象管理组织(OMG)的对象实务服务(OTS),SunMicrosystems 的 Transaction Service(JTS)、Java Transaction API(JTA),开发组(X/Open)的 XA 接口。

59、Comparable 和 Comparator 接口的区别?

        Comparable 接口只包含一个 compareTo()方法。这个方法可以个给两个对象排序。具体来说,它返回负数,0,正数来表明输入对象小于,等于,大于已经存在的对象。Comparator 接口包含 compare()和 equals()两个方法。

60、switch 能否作用在 byte、long、string 上? 

         switch 可作用在 char、byte、short、int switch 可作用于 char、byte、short、int 的包装类上switch 不可作用于 long、double、float、boolean,包括他们的包装类 switch 中可以是字符串类型,String(Java1.7 以后才可以作用在 String 上)switch 可以是枚举类型(JDK1.5 之后)

61、jdk 中哪些类是不能继承的?

        不能继承的是类是那些用 final 关键字修饰的类。一般比较基本的类型或防止扩展类无意间破坏原来方法的实现的类型都应该是 final 的,在 jdk 中System,String,StringBuffer 等都是基本类型。

62、Set 里的元素是不能重复的,那么用什么方法来区分重复与否呢?

        Set 里的元素是不能重复的,元素重复与否是使用 equals()方法进行判断的。equals()和==方法决定引用值是否指向同一对象 equals()在类中被覆盖,为的是当两个分离的对象的内容和类型相配的话,返回真值。

63、JDK 和 JRE 的区别是什么?

        Java 运行时环境(JRE)是将要执行 Java 程序的 Java 虚拟机。它同时也包含了执行 applet需要的浏览器插件。Java 开发工具包(JDK)是完整的 Java 软件开发包,包含了 JRE,编译器和其他的工具(比如:JavaDoc,Java 调试器),可以让开发者开发、编译、执行 Java 应用程序。

64、是否可以在 static 环境中访问非 static 变量?

        static 变量在 Java 中是属于类的,它在所有的实例中的值是一样的。当类被 Java 虚拟机载入的时候,会对 static 变量进行初始化。如果你的代码尝试不用实例来访问非 static的变量,编译器会报错,因为这些变量还没有被创建出来,还没有跟任何实例关联上。

65、Java 支持多继承么?

        不支持,Java 不支持多继承。每个类都只能继承一个类,但是可以实现多个接口。

66、什么是迭代器(Iterator)?

        Iterator 接口提供了很多对集合元素进行迭代的方法。每一个集合类都包含了可以返回迭代器实例的 迭代方法。迭代器可以在迭代的过程中删除底层集合的元素。克隆(cloning)或者是序列化(serialization)的语义和含义是跟具体的实现相关的。因此,应该由集合类的具体实现来决定如何被克隆或者是序列化。

67、Iterator 和 ListIterator 的区别是什么?

        下面列出了他们的区别: Iterator 可用来遍历 Set 和 List 集合,但是 ListIterator 只能用来遍历 List。Iterator 对集合只能是前向遍历,ListIterator 既可以前向也可以后向。ListIterator 实现了 Iterator 接口,并包含其他的功能,比如:增加元素,替换元素,获取前一个和后一个元素的索引,等等。

68、Enumeration 接口和 Iterator 接口的区别有哪些?

         Enumeration 速度是 Iterator 的 2 倍,同时占用更少的内存。但是,Iterator 远远比Enumeration 安全,因为其他线程不能够修改正在被 iterator 遍历的集合里面的对象。同时,Iterator 允许调用者删除底层集合里面的元素,这对 Enumeration 来说是不可能的。

69、List, Set, Map 是否继承自 Collection 接口?

        只有 List 和 Set 接口继承于 Collection 接口,Map 是与 Collection 并列的接口概念

70、字符串常量池到底存在于内存空间的哪里? jdk 6.0 字符串常量池在方法区,方法区的具体体现可以看做是堆中的永久区。jdk 7.0 java 虚拟机规范中不再声明方法区,字符串常量池存放在堆空间中jdk 8.0 java 虚拟机规范中又声明了元空间,字符串常量池存放在元空间中

71、Java 中的编译期常量是什么?使用它又什么风险?

        公共静态不可变(public static final )变量也就是我们所说的编译期常量,这里的 public 可选的。实际上这些变量在编译时会被替换掉,因为编译器知道这些变量的值,并且知道这些变量在运行时不能改变。这种方式存在的一个问题是你使用了一个内部的或第三方库中的公有编译时常量,但是这个值后面被其他人改变了,但是你的客户端仍然在使用老的值,甚至你已经部署了一个新的 jar。为了避免这种情况, 当你在更新依赖 JAR 文件时,确保重新编译你的程序。

72、用哪两种方式来实现集合的排序?

        你可以使用有序集合,如 TreeSet 或 TreeMap,你也可以使用有顺序的的集合,如 list,然后通过 Collections.sort() 来排序。

73、说出 JDK 1.7 中的三个新特性?

        虽 然 JDK 1.7 不 像 JDK 5 和 8 一 样的 大版 本 ,但 是, 还 是有 很多 新的 特 性, 如try-with-resource 语句,这样你在使用流或者资源的时候,就不需要手动关闭,Java 会自动关闭。Fork-Join 池某种程度上实现 Java 版的 Map-reduce。允许 Switch 中有 String 变量和文本。菱形操作符(<>)用于类型推断,不再需要在变量声明的右边申明泛型,因此可以写出可读写更强、更简洁的代码。另一个值得一提的特性是改善异常处理,如允许在同一个catch 块中捕获多个异常。

74、说出 5 个 JDK 1.8 引入的新特性?

        Lambda表达式

        函数式接口

        方法引用和构造器调用

        Stream API

        接口中的默认方法和静态方法

        新时间日期API

75.ArrayList 源码分析?

        (1)ArrayList 是一种变长的集合类,基于定长数组实现,使用默认构造方法初始化出来的容量是 10(1.7 之后都是延迟初始化,即第一次调用 add 方法添加元素的时候才将elementData 容量初始化为 10)。

        (2)ArrayList 允许空值和重复元素,当往 ArrayList 中添加的元素数量大于其底层数组容量时,其会通过扩容机制重新生成一个更大的数组。ArrayList 扩容的长度是原长度的 1.5 倍

        (3)由于 ArrayList 底层基于数组实现,所以其可以保证在 O(1) 复杂度下完成随机查找操作。

        (4)ArrayList 是非线程安全类,并发环境下,多个线程同时操作 ArrayList,会引发不可预知的异常或错误。

        (5)顺序添加很方便

        (6)删除和插入需要复制数组,性能差(可以使用 LinkindList)

        (7)Integer.MAX_VALUE - 8 :主要是考虑到不同的 JVM,有的 JVM 会在加入一些数据头,当扩容后的容量大于 MAX_ARRAY_SIZE,我们会去比较最小需要容量和 MAX_ARRAY_SIZE 做比较,如果比它大, 只能取 Integer.MAX_VALUE,否则是 Integer.MAX_VALUE -8。 这个是从 jdk1.7 开始才有的

76.HashMap 源码分析?

        jdk1.8 之前 list + 链表 jdk1.8 之后 list + 链表(当链表长度到 8 时,转化为红黑树)HashMap 的扩容因子 默认 0.75,也就是会浪费 1/4 的空间,达到扩容因子时,会将 list 扩容一倍,0.75 是时间与空间一个平衡值;

77、ConcurrentHashMap 源码分析?

        ConcurrentHashMap 所使用的锁分段技术,首先将数据分成一段一段的存储,然后给每一段数据配一把锁,当一个线程占用锁访问其中一个段数据的时候,其他段的数据也能被其他线程访问。有些方法需要跨段,比如 size()和 containsValue(),它们可能需要锁定整个表而而不仅仅是某个段,这需要按顺序锁定所有段,操作完毕后,又按顺序释放所有段的锁。这里“按顺序”是很重要的,否则极有可能出现死锁,在 ConcurrentHashMap 内部,段数组是 final 的,并且其成员变量实际上也是 final 的,但是,仅仅是将数组声明为 final 的并不保证数组成员也是 final 的,这需要实现上的保证。这可以确保不会出现死锁,因为获得锁的顺序是固定的。ConcurrentHashMap 是由 Segment 数组结构和 HashEntry 数组结构组成。Segment 是一种可重入锁 ReentrantLock,在 ConcurrentHashMap 里扮演锁的角色,HashEntry 则用于存储键值对数据。一个 ConcurrentHashMap 里包含一个 Segment 数组,Segment 的结构和 HashMap类似,是一种数组和链表结构, 一个 Segment 里包含一个 HashEntry 数组,每个 HashEntry是一个链表结构的元素, 每个 Segment 守护者一个 HashEntry 数组里的元素,当对 HashEntry数组的数据进行修改时,必须首先获得它对应的 Segment 锁。

  • 6
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

失忆机器

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值