ArrayList和Vector

1. 同步性

1.1. ArrayList 是非同步的

ArrayList阿 是非同步的,即它不支持线程安全操作。如果多个线程同时访问一个 ArrayList` 对象并且至少一个线程对其进行了修改(如插入、删除操作),而没有使用外部同步机制,那么会导致不确定的行为。

示例:

import java.util.ArrayList;

public class ArrayListExample {
    public static void main(String[] args) {
        ArrayList<Integer> list = new ArrayList<>();
        list.add(1);
        list.add(2);
        list.add(3);
        // 非线程安全的
    }
}

在多线程环境中使用 ArrayList 时,需要手动同步。例如,可以使用 Collections.synchronizedList() 方法将 ArrayList 包装成同步的列表:

import java.util.Collections;
import java.util.List;

public class SynchronizedArrayListExample {
    public static void main(String[] args) {
        List<Integer> list = Collections.synchronizedList(new ArrayList<>());
        list.add(1);
        list.add(2);
        list.add(3);
        // 线程安全的
    }
}
1.2. Vector 是同步的

Vector 是线程安全的。它的所有公共方法都是同步的,因此可以安全地在多线程环境中使用。但是,由于同步带来的性能开销,Vector 的操作比 ArrayList 慢。

示例:

import java.util.Vector;

public class VectorExample {
    public static void main(String[] args) {
        Vector<Integer> vector = new Vector<>();
        vector.add(1);
        vector.add(2);
        vector.add(3);
        // 线程安全的
    }
}

由于 Vector 的每个方法都被同步,因此即使在多线程环境中,Vector 也能保证一致性。

2. 性能

由于 Vector 是同步的,而 ArrayList 是非同步的,因此在大多数情况下,ArrayList 的性能要优于 Vector。在单线程或读多写少的多线程环境中,ArrayList 是更好的选择。

性能比较:

  • ArrayList:因为不涉及同步操作,ArrayList 在单线程环境中的性能更高。
  • VectorVector 因为同步机制,每次操作都需要获取锁,在多线程环境中可能会产生锁竞争,从而导致性能下降。

3. 扩容方式

ArrayListVector 的内部数组存满时,它们会自动扩容,但扩容的策略有所不同。

3.1. ArrayList 的扩容方式

ArrayList 每次扩容时,容量会增加 50%(即原容量的 1.5 倍)。具体来说,当 ArrayList 的容量不足以容纳新元素时,它会创建一个比原数组大 50% 的新数组,并将原数组中的元素复制到新数组中。

示例:

import java.util.ArrayList;

public class ArrayListCapacityExample {
    public static void main(String[] args) {
        ArrayList<Integer> list = new ArrayList<>(10);  // 初始容量为10
        for (int i = 0; i < 11; i++) {
            list.add(i);
        }
        // 当第11个元素被添加时,ArrayList会扩容
    }
}
3.2. Vector 的扩容方式

Vector 的默认扩容方式是将容量翻倍(即原容量的 2 倍)。Vector 还允许通过构造函数指定扩容的增量大小(capacityIncrement),如果没有指定,则默认是原容量的 100%。

示例:

import java.util.Vector;

public class VectorCapacityExample {
    public static void main(String[] args) {
        Vector<Integer> vector = new Vector<>(10);  // 初始容量为10
        for (int i = 0; i < 11; i++) {
            vector.add(i);
        }
        // 当第11个元素被添加时,Vector会扩容,默认情况下容量翻倍
    }
}

4. 历史背景和使用场景

4.1. ArrayList 的背景

ArrayList 是 Java 2 (JDK 1.2) 中引入的,作为 Vector 的非同步替代品。它提供了类似 Vector 的功能,但在单线程环境下性能更好。ArrayListList 接口的主要实现类之一,也是目前最常用的集合类之一。

4.2. Vector 的背景

Vector 是 Java 1.0 中引入的,当时 Java 没有 Collection 框架。Vector 是最早的集合类之一,并且设计之初就考虑了线程安全问题。因此,Vector 的所有方法都是同步的。

随着 Java 的发展,引入了 ArrayList,逐渐取代了 Vector 在大多数场景中的使用。Vector 现在已经很少使用,更多的是为了向后兼容旧代码。

5. 使用建议

5.1. 选择 ArrayList
  • 单线程环境:在单线程环境或线程安全不是问题的场景中,ArrayList 是更好的选择,性能更优。
  • 性能要求高:如果需要高性能,特别是在大量读写操作时,ArrayListVector 更合适。
  • 新开发项目:在新开发项目中,ArrayList 应该是首选,Vector 由于其同步开销和历史原因,通常不推荐使用。
5.2. 选择 Vector
  • 多线程环境:如果必须使用同步的列表,且不希望手动实现同步,Vector 是一个选项。不过,在现代开发中,更好的做法是使用Collections.synchronizedList()ArrayList进行包装,或直接使用 CopyOnWriteArrayList
  • 兼容旧代码:如果维护的代码依赖于 Vector,且没有强烈的性能要求,可以继续使用 Vector 以避免大规模重构。

6. 替代方案

在多线程环境下,Java 提供了一些比 Vector 更现代的替代方案:

  • CopyOnWriteArrayList:在多线程环境中,CopyOnWriteArrayList 是一个更好的选择。它使用了一种不同的线程安全策略,在写操作时会复制整个底层数组,适合读多写少的场景。

  • Collections.synchronizedList:可以使用 Collections.synchronizedList() 方法将 ArrayList 包装成线程安全的列表,获得与 Vector 类似的效果。

示例:CopyOnWriteArrayList

import java.util.concurrent.CopyOnWriteArrayList;

public class CopyOnWriteArrayListExample {
    public static void main(String[] args) {
        CopyOnWriteArrayList<Integer> list = new CopyOnWriteArrayList<>();
        list.add(1);
        list.add(2);
        list.add(3);
        // 线程安全的
    }
}

7. 总结

ArrayListVector 都是基于动态数组的集合类,但它们在同步性、性能、扩容方式和历史背景上存在显著差异:

  • 同步性ArrayList 是非同步的,Vector 是同步的。
  • 性能:由于同步开销,ArrayList 的性能通常优于 Vector
  • 扩容方式ArrayList 扩容为原容量的 1.5 倍,而 Vector 默认扩容为原容量的 2 倍。
  • 历史背景Vector 是早期的集合类,设计时考虑了线程安全,而 ArrayList 是为了提供更高性能的非同步列表。

在现代 Java 开发中,ArrayList 是更常用的选择。Vector 通常只在需要向后兼容旧代码或必须使用同步集合的情况下使用。对于多线程环境,建议使用 CopyOnWriteArrayList 或通过 Collections.synchronizedListArrayList 进行同步包装。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

Flying_Fish_Xuan

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

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

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

打赏作者

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

抵扣说明:

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

余额充值