一、AtomicInteger简介
在多线程编程中,当多个线程同时访问同一个变量时,如果不加以限制,就会存在竞争条件,导致变量值不确定。为了解决这个问题,Java提供了一组原子类(Atomic class),其中一种就是AtomicInteger。 AtomicInteger是一个用于带符号整型数值(int)的原子类。它能够在不使用锁的情况下保证整型变量的原子性操作。AtomicInteger定义了一些原子操作方法,通过这些方法能够实现变量的原子操作,如addAndGet、compareAndSet、decrementAndGet、getAndAdd等,从而能够实现线程安全。
二、AtomicInteger与线程安全
使用AtomicInteger能够保证多线程同时对变量进行的操作是原子的。原子操作是指一组操作不会被其他线程中断,保证整个操作一定能够得到完成。这种机制是基于CAS(Compare And Swap)实现的。 在AtomicInteger中,CAS操作是通过compareAndSet方法实现的。当多个线程同时调用compareAndSet方法,只有一个线程能够修改变量。如果同时有多个线程调用该方法,会有一个线程成功修改变量,其他线程将返回false,随后再进行重试。因此,使用AtomicInteger能够避免竞争条件,实现线程安全。
三、AtomicInteger的常用方法
1、get方法:获取当前AtomicInteger的值。 AtomicInteger count = new AtomicInteger(0); int currentCount = count.get(); 2、addAndGet方法:将指定值与当前的AtomicInteger的值相加,并返回新的值。 AtomicInteger count = new AtomicInteger(0); int result = count.addAndGet(2); 3、compareAndSet方法:比较当前值是否等于expect的值,如果相等则将当前值设置为update,并返回true,否则返回false。 AtomicInteger count = new AtomicInteger(0); boolean flag = count.compareAndSet(0, 2); 4、decrementAndGet方法:将当前值减1,并返回新的值。 AtomicInteger count = new AtomicInteger(2); int result = count.decrementAndGet(); 5、getAndAdd方法:先获取当前AtomicInteger的值,再将指定值与当前值相加,并返回原来的值。 AtomicInteger count = new AtomicInteger(0); int result = count.getAndAdd(2);
四、AtomicInteger的使用场景
1、在计数器中使用:通过AtomicInteger能够实现多线程对计数器的安全操作,避免竞争条件。 AtomicInteger counter = new AtomicInteger(0); public void increment() { counter.incrementAndGet(); } public int getCount() { return counter.get(); } 2、在保证线程安全的数据结构中使用:比如Stack、Queue等数据结构,通过使用AtomicInteger能够保证多线程操作这些数据结构的时候不会出现竞争条件。 Queue<String> queue = new ConcurrentLinkedQueue<>(); AtomicInteger count = new AtomicInteger(0); public void enqueue(String item) { queue.offer(item); count.incrementAndGet(); } public String dequeue() { String item = queue.poll(); if (item != null) { count.decrementAndGet(); } return item; } public int getCount() { return count.get(); } 3、在某些需要高效的算法中使用:原子类的操作比锁操作的性能更好,所以在某些需要高效的算法中,可以选择使用原子类。
五、小结
Java中的AtomicInteger是一个用于带符号整型数值的原子类,能够在不使用锁的情况下保证原子性操作,从而实现线程安全。适用于计数器、保证线程安全的数据结构和高效算法等场景。