面试知识点总结之集合框架HashSet/ArrayList/LinkedList/String/StringBuffer/StringBuilder

集合框架之HashSet如何保证元素唯一性原理

  1. HashSet原理
    我们使用Set集合都是需要去掉重复元素的,如果在存储的时候逐个equals()比较,效率较低,哈希算法提高了去重复的效率,降低了使用equals()方法的次数
    当HashSet调用add()方法存储对象的时候,先调用对象的HashCode()方法得到一个哈希值,然后在集合中查找是否有哈希值相同的对象,如果没有哈希值相同的对象就直接存入集合;如果有哈希值相同的对象,就和哈希值相同的对象逐个进行equals()比较,比较结果为false就存入,true则不存。
  2. 将自定义的对象存入HashSet去重复
    类中必须重写hashcode()和equals()方法
    hashCode():属性相同的对象返回值必须相同,属性值不同的返回值尽量不同(提高效率)
    equals():属性相同返回true,属性不同返回false,返回false的时候存储(注意存储自定义对象去重时必须同时重写equals()和hashCode()方法,因为equals()是按照对象地址值比较的)

为什么arrayList查询效率高,删除效率慢
ArrayList查询效率高:ArrayList是连续存放元素的,找到第一个元素的首地址,再加上每个元素的占据的字节大小就能定位到对应元素
LinkedList插入效率高:因为执行插入删除操作时,只需要操作引用即可,元素不需要移动元素,他们分布在内存的不同地方,通过引用来互相关联起来,而ArrayList需要移动元素,效率低。

ArrayList的数据结构,底层数据结构就是一个数组,数组元素的类型为Object类型,对ArrayList的所有操作底层都是基于数组的

ArrayList的线程安全性:对ArrayList添加元素的操作分两步进行,即第一步先在Object[size]的位置上存放需要添加的元素;第二步将size的值加1,由于这个过程在多线程环境下时不能保证原子性的,因此,ArrayList在多线程环境下时线程不安全的。

举例说明:在单线程运行情况下,如果size=0,添加一个元素后,此元素在位置0,而且size=1;而在多线程下,如两个线程,线程A先将元素存放在0,但此时CPU调度线程A暂停,线程B得到运行机会。线程B也向此ArrayList添加元素,因此Size仍然等于0(注意,假设的时添加一个元素需要两个步骤,而线程A仅完成了步骤1)所以线程B也将元素存放在位置0.然后线程A和线程B都继续运行,都增加Size的值,那好,现在ArrayList,元素实际上只有一个,存放在位置0,而size却等于2,这就是线程不安全。
如果非要在多线程下使用ArrayList,需要保证线程安全,通常有两种解决方法,第一,使用synchronized关键字,第二,可以用Collections类中的静态方法synchronizedList();对ArrayList进行调用即可。
Arraylist继承Abstractlist抽象父类,实现了List接口(规定了list的操作规范),RandomAccess(可随机访问),Cloneable(可拷贝)Serializable(可序列化)

String:java.lang下的一个类,不是基本类型,String时不可变的,JVM使用字符串池来存储所有字符串对象
String时不可变类,当对String进行操作时,总是会创建新的字符串,操作String很耗费资源,所以提供了两个工具类StringBuffer和StringBuilder
StringBuffer和StringBuilder是可变类
String不可变类优点,1. 所以在多线程中使用是安全的,我们不需要做任何其他同步操作 2. String是不可变的,它的值也不能被改变,所以用来存储数据密码很安全 3. 因为不可变的,所以在Java运行时可节省大量Java堆空间。因为不同的字符串变量可以引用池中相同的字符串

原文地址:https://www.cnblogs.com/cgy-home/p/14525870.html