Java实现同步锁的四种方式

135 阅读2分钟

在Android(及Java)中,有几种常见的方式可以实现同步锁,以确保线程安全。以下是几种不同的同步锁实现方式的示例。

1. 使用synchronized关键字

方法同步

如前面的例子所示,可以直接在方法声明上添加synchronized关键字,使得整个方法成为同步方法。

javaCopy Code
public synchronized void increment() {
    // 同步代码
}

代码块同步

如果只需要对方法中的一部分代码进行同步,可以使用synchronized代码块。

javaCopy Code
public void increment() {
    synchronized (this) {
        // 需要同步的代码
    }
}

2. 使用ReentrantLock

ReentrantLock是java.util.concurrent.locks包中提供的一种可重入互斥锁,它具有与synchronized相似的基本行为和语义,但比synchronized更加灵活。

javaCopy Code
import java.util.concurrent.locks.ReentrantLock;

public class Counter {
    private final ReentrantLock lock = new ReentrantLock();
    private int count = 0;

    public void increment() {
        lock.lock();  // 获取锁
        try {
            count++;
        } finally {
            lock.unlock();  // 释放锁
        }
    }
}

3. 使用AtomicInteger

对于简单的计数器,还可以使用java.util.concurrent.atomic.AtomicInteger类。这个类利用CAS(compare-and-swap)操作提供了原子性操作,避免了同步的开销,适合于高并发情况。

javaCopy Code
import java.util.concurrent.atomic.AtomicInteger;

public class Counter {
    private AtomicInteger count = new AtomicInteger(0);

    public void increment() {
        count.incrementAndGet();
    }

    public int getCount() {
        return count.get();
    }
}

4. 使用synchronized关键字同步静态方法

当需要对静态方法进行同步时,可以将synchronized关键字用于静态方法。这时,锁定的是类的Class对象。

javaCopy Code
public class Counter {
    private static int count = 0;

    public static synchronized void increment() {
        count++;
    }
}

5. 使用synchronized代码块同步静态变量

如果需要对静态变量的某个操作进行同步,可以使用synchronized代码块,并将Class对象作为锁对象。

javaCopy Code
public class Counter {
    private static int count = 0;

    public void increment() {
        synchronized (Counter.class) {
            count++;
        }
    }
}

每种方法都有其适用场景。synchronized关键字是最基本的同步机制,简单易用。ReentrantLock提供了更多高级功能,如尝试非阻塞获取锁、公平锁等。AtomicInteger等原子类适用于单一变量的并发操作,可以减少同步的开销。选择哪种方式取决于具体需求和场景