三、List接口

List接口是Collection接口的子接口,存储元素有序可重复,它有一些自己特有的方法。

1.List接口常用特有方法

  • void add(int index, Object element):向指定下标位置添加元素,但效率较低,很少使用
  • Object set(int index, Object element):更改指定位置的元素
  • Object get(int index):根据下标获取元素
  • int indexOf(Object o):获取指定对象第一次出现初的索引
  • int lastIndexOf(Object o):获取指定对象最后一次出现处的索引
  • Object remove(int index):删除指定下标位置的元素

    2.List集合特有遍历方法

    因为List集合有下标,所以List集合可以通过下标遍历。

    1. public class Test {
    2. public static void main(String[] args) {
    3. List mylist = new ArrayList();//创建List类型集合
    4. mylist.add("A");
    5. mylist.add("B");
    6. mylist.add("C");
    7. mylist.add("C");
    8. mylist.add(1, "C");//向指定位置插入元素
    9. for (int i = 0; i < mylist.size(); i++) {
    10. System.out.println(mylist.get(i));
    11. }
    12. }
    13. }

    3.ArrayList集合初始化容量及扩容

    3.1 特性

  • ArrayList集合默认初始化容量为10。

  • ArrayList集合底层是一个Object[ ]数组。
  • 满了之后扩容,扩容到原容量的1.5倍。
  • 检索效率比较高,随机增删效率低,向数组末尾增加元素效率很高,不受影响。

    3.2 ArrayList集合构造方法

  • ArrayList():构造一个初始容量为10的空列表。

  • ArrayList(Collection c):构造一个包含指定Collection的元素的列表,这些元素按照该Collection的迭代器返回它们的顺序排列的。
  • ArrayList(int initialCapacity):构造一个具有指定初始容量的空列表。

    1. public class Test {
    2. public static void main(String[] args) {
    3. List list1 = new ArrayList();//构造一个初始容量为10的数组
    4. List list2 = new ArrayList(50);//构造一个指定容量的数组
    5. Collection c = new HashSet();
    6. c.add(1);
    7. c.add(2);
    8. c.add(3);
    9. //通过这个方法将HashSet集合转换为ArrayList集合
    10. List list3 = new ArrayList(c);
    11. for (int i = 0; i < list3.size(); i++) {
    12. System.out.println(list3.get(i));
    13. }
    14. }
    15. }

    3.3 面试问题

    这么多集合中,哪个集合用的最多?
    答:ArrayList集合,因为往数组末尾添加元素效率不受影响,另外,我们检索/查找某个元素的操作比较多。

    4.LinkedList集合

    4.1 特性

  • 集合底层是双向链表,但同样有下标,可根据索引随机访问元素。

  • 随机增删效率较高,检索效率较低。
  • 链表中的元素在存储上内存地址不连续。

    4.2 使用

    5.Vector集合

  • Vector集合的底层是数组,但因为它所有方法都实现了线程同步的功能,且实现机制不好,所以各方面性能都很差,极少使用。

  • 初始化容量为10,扩容为原来的2倍。
  • 使用方法和ArrayList没有很大区别。

    6.线程不安全的ArrayList转化为线程安全

  • java.util.Collection是集合接口。

  • java.util.Collections是集合工具类。

使用java.util.Collections集合工具类可以将线程不安全的ArrayList转化为线程安全的。

  1. public class Test {
  2. public static void main(String[] args) {
  3. List list = new ArrayList();//线程不安全的
  4. Collections.synchronizedList(list);//变成线程安全的
  5. }
  6. }

四、Set集合

Set集合不允许包含重复元素,如果把两个相同元素加入到同一个Set集合中,则添加操作失败,add()方法返回false,且新元素不会被加入。Set集合和Collection基本相同,没有提供额外的方法。

1.HashSet类

HashSet是Set接口的典型实现,大多数时候使用Set集合时就是使用这个实现类。具有如下特点:

  • 不能保证元素的排列顺序,顺序可能与添加顺序不同,顺序也有可能发生变化。
  • HashSet不是同步的,如果多个线程同时访问一个HashSet,则必须通过代码来保证同步。
  • 集合元素值可以是null。

    当向HashSet集合中存入一个元素时,HashSet会调用该对象的hashCode()方法来得到该对象的hashCode值,然后根据该hashCode值决定该对象在HashSet中的存储位置。也就是说,HashSet集合判断两个元素是否相等的标准是两个对象通过equals()方法比较相等,并且两个对象的hashCode()方法返回值也相等。所以,如果需要把两个对象保存到HashSet集合中,重写这个类的equals()方法和hashCode()方法时,应尽量保证这两个对象通过equals()方法返回true时,它们的hashCode()方法返回值也相等。否则,如果两个对象通过equals()方法比较相等,但hashCode()方法比较不相等时,两个对象都可以添加成功,这与Set集合的规则冲突。

    2.TreeSet类

  • 无序不可重复,但存储的元素可以自动按照大小顺序排序,称为可排序集合。

    1. public class Test {
    2. public static void main(String[] args) {
    3. Set<String> strs = new TreeSet<>();
    4. strs.add("B");
    5. strs.add("D");
    6. strs.add("A");
    7. strs.add("K");
    8. //自动排序输出
    9. for (String s: strs) {
    10. System.out.println(s);
    11. }
    12. }
    13. }
    14. A
    15. B
    16. D
    17. K

    五、Map接口

  • Map和Collection没有继承关系。

  • key和value都是存储引用数据类型。

    1.Map接口中常用方法