本文共 3742 字,大约阅读时间需要 12 分钟。
声明:本文是《 》的第八章, 作者: Javier Fernández González 译者:郑玉婷
校对:方腾飞
Lock 接口是Java 并发 API提供的最基本的机制来同步代码块。它允许定义临界区。临界区是代码块可以共享资源,但是不能被多个线程同时执行。此机制是通过Lock 接口和 ReentrantLock 类实现的。
在这个指南,你将学习从Lock对象可以获取的信息和如何获取这些信息。
准备
指南中的例子是使用Eclipse IDE 来实现的。如果你使用Eclipse 或者其他的IDE,例如NetBeans, 打开并创建一个新的java项目。
怎么做呢…
按照这些步骤来实现下面的例子:
package tool;import java.util.Collection;import java.util.concurrent.TimeUnit;import java.util.concurrent.locks.Lock;import java.util.concurrent.locks.ReentrantLock;//1. 创建一个类,名为 MyLock ,扩展 ReentrantLock 类。public class MyLock extends ReentrantLock { // 2. 实现 getOwnerName() 方法。此方法使用Lock类的保护方法 getOwner(), 返回控制锁的线程(如果存在)的名字。 public String getOwnerName() { if (this.getOwner() == null) { return "None"; } return this.getOwner().getName(); } // 3. 实现 getThreads() 方法。此方法使用Lock类的保护方法 getQueuedThreads(),返回在锁里的线程的 queued // list。 public CollectiongetThreads() { return this.getQueuedThreads(); } // 4. 创建一个类,名为 Task,实现 Runnable 接口. public class Task implements Runnable { // 5. 声明一个私有 Lock 属性,名为 lock。 private Lock lock; // 6. 实现类的构造函数,初始化它的属性值。 public Task(Lock lock) { this.lock = lock; } // 7. 实现 run() 方法。创建迭代5次的for循环。 @Override public void run() { for (int i = 0; i < 5; i++) { // 8. 使用lock()方法获取锁,并打印一条信息。 lock.lock(); System.out.printf("%s: Get the Lock.\n", Thread.currentThread() .getName()); // 9. 让线程休眠 500 毫秒。使用 unlock() 释放锁并打印一条信息。 try { TimeUnit.MILLISECONDS.sleep(500); System.out.printf("%s: Free the Lock.\n", Thread .currentThread().getName()); } catch (InterruptedException e) { e.printStackTrace(); } finally { lock.unlock(); } } } } // 10. 创建例子的主类通过创建一个类,名为 Main 并添加 main()方法。 public static void main(String[] args) throws Exception { // 11. 创建 MyLock 对象,名为 lock。 MyLock lock = new MyLock(); // 12. 创建有5个Thread对象的 array。 Thread threads[] = new Thread[5]; // 13. 创建并开始5个线程来执行5个Task对象。 for (int i = 0; i < 5; i++) { Task task = lock.new Task(lock); threads[i] = new Thread(task); threads[i].start(); } // 14. 创建迭代15次的for循环。 for (int i = 0; i < 15; i++) { // 15. 把锁的拥有者的名字写入操控台。 System.out.printf("Main: Logging the Lock\n"); System.out.printf("************************\n"); System.out.printf("Lock: Owner : %s\n", lock.getOwnerName()); // 16. 显示锁queued的线程的号码和名字。 System.out.printf("Lock: Queued Threads: %s\n", lock.hasQueuedThreads()); // 译者注:加上 System if (lock.hasQueuedThreads()) { System.out.printf("Lock: Queue Length: %d\n", lock.getQueueLength()); System.out.printf("Lock: Queued Threads: "); Collection lockedThreads = lock.getThreads(); for (Thread lockedThread : lockedThreads) { System.out.printf("%s ", lockedThread.getName()); } System.out.printf("\n"); } // 17. 显示关于Lock对象的公平性和状态的信息。 System.out.printf("Lock: Fairness: %s\n", lock.isFair()); System.out.printf("Lock: Locked: %s\n", lock.isLocked()); System.out.printf("************************\n"); // 18. 让线程休眠1秒,并合上类的循环。 TimeUnit.SECONDS.sleep(1); } }}
它是如何工作的…
在这个指南里,你实现的MyLock类扩展了ReentrantLock类来返回信息,除此之外获得不到这些信息 ,因为ReentrantLock 类里的数据都是保护类型的。 通过MyLock类实现的方法:
我们还使用了 ReentrantLock 类里实现的其他方法:
更多…
ReentrantLock 类还有其他方法也是用来获取Lock对象的信息的:
参见
文章转自
转载地址:http://tirnl.baihongyu.com/