Java 顯式鎖

2018-02-28 15:45 更新

Java線程教程 - Java顯式鎖


顯式鎖定機(jī)制可以用于協(xié)調(diào)對(duì)多線程環(huán)境中的共享資源的訪問。

在java.util.concurrent.locks包中聲明的Lock接口定義了顯式鎖定操作。

ReentrantLock類在同一個(gè)包中,是Lock接口的具體實(shí)現(xiàn)。

Lock接口聲明如下:

public interface Lock {
  void lock();

  Condition newCondition();

  void lockInterruptibly() throws InterruptedException;

  boolean tryLock();

  boolean tryLock(long time, TimeUnit unit) throws InterruptedException;

  void unlock();
}

lock()方法獲取一個(gè)鎖的行為與使用synchronized關(guān)鍵字相同。

我們必須在完成鎖定后通過調(diào)用Lock接口的unlock()方法釋放鎖定。

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class Main {
  // Instantiate the lock object
  private Lock myLock = new ReentrantLock();

  public void updateResource() {

    try {
      // Acquire the lock
      myLock.lock();
    } finally {
      // Release the lock
      myLock.unlock();
    }
  }
}

例子

下面的代碼模擬哲學(xué)家,假設(shè)ReentrantLock類的一個(gè)對(duì)象表示一個(gè)fork。

import java.util.concurrent.locks.Lock;

class Philosopher {
  private Lock leftFork;
  private Lock rightFork;
  private String name; // Philosopher"s name

  public Philosopher(Lock leftFork, Lock rightFork, String name) {
    this.leftFork = leftFork;
    this.rightFork = rightFork;
    this.name = name;
  }

  public void think() {
    System.out.println(name + "  is thinking...");
  }

  public void eat() {
    if (leftFork.tryLock()) {
      try {
        if (rightFork.tryLock()) {
          try {
            System.out.println(name + "  is eating...");
          } finally {
            rightFork.unlock();
          }
        }
      } finally {
        leftFork.unlock();
      }
    }
  }
}

例2

ReentrantReadWriteLock類是ReadWriteLock接口的實(shí)現(xiàn)。只有一個(gè)線程可以保持ReentrantReadWriteLock的寫鎖,而多個(gè)線程可以保持其讀鎖。

下面的代碼演示了ReentrantReadWriteLock的用法。

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantReadWriteLock;

public class Main {
  private int value;
  private ReentrantReadWriteLock rwLock = new ReentrantReadWriteLock();
  private Lock rLock = rwLock.readLock();
  private Lock wLock = rwLock.writeLock();

  public Main(int value) {
    this.value = value;
  }

  public int getValue() {
    rLock.lock();
    try {
      return this.value;
    } finally {
      rLock.unlock();
    }
  }

  public void setValue(int value) {
    wLock.lock();
    try {
      this.value = value;
    } finally {
      wLock.unlock();
    }
  }
}
以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)