Java Lock--reentrantlock

Source: Internet
Author: User

Reprint Please specify source: http://www.cnblogs.com/skywang12345/p/3496101.html

Reentrantlock Introduction

Reentrantlock is a reentrant mutex, also known as an "exclusive lock."

As the name implies, Reentrantlock locks can only be held by a single thread lock at the same point in time, whereas reentrant means that reentrantlock locks can be obtained multiple times by individual threads.
Reentrantlock is divided into " fair lock " and " non-fair lock ". The difference between them is fair in the mechanism of acquiring locks. "Locks" are designed to protect competing resources, prevent multiple threads from manipulating threads simultaneously, and reentrantlock can only be fetched by one thread at a time (when a thread acquires a "lock", other threads must wait). The Reentraantlock is a FIFO waiting queue to manage all threads that acquire the lock. Under the mechanism of "fair lock", threads queue to acquire the lock, while the "unfair lock" acquires the lock at the beginning of the queue, regardless of whether the lock is in the acquired state.

List of Reentrantlock functions
Creates a reentrantlock, which by default is an "unfair lock." Reentrantlock ()//Create policy is the reentrantlock of fair. Fair is true to indicate a fair lock, and fair to false to indicate a non-fair lock. Reentrantlock (Boolean Fair)//queries the number of times that the current thread holds this lock. int Getholdcount ()//returns the thread that currently owns this lock, or null if the lock is not owned by any thread. Protected thread GetOwner ()//Returns a collection that contains the thread that may be waiting to acquire this lock. Protected collection<thread> getqueuedthreads ()//Returns the estimated number of threads that are waiting to get this lock. int getqueuelength ()//Returns a collection that contains those threads that may be waiting for a given condition related to this lock. Protected collection<thread> getwaitingthreads (Condition Condition)//Returns the number of thread estimates waiting for the given condition associated with this lock. int Getwaitqueuelength (Condition Condition)//queries whether a given thread is waiting to acquire this lock. Boolean hasqueuedthread (thread thread)//query whether some threads are waiting to acquire this lock. Boolean hasqueuedthreads ()//queries whether some threads are waiting for a given condition related to this lock. Boolean haswaiters (Condition Condition)//returns True if the "fair lock" returns false otherwise. Boolean Isfair ()//queries whether the current thread holds this lock. Boolean isheldbycurrentthread ()//queries whether this lock is persisted by any thread. Boolean isLocked ()//Gets the lock. void lock ()//Gets the lock if the current thread is not interrupted. void lockinterruptibly ()//Returns the Condition instance used with this Lock instance. Condition newcondition ()//The lock is acquired only if the lock is not persisted by another thread at the time of the call. Boolean TRylock ()//If the lock is not persisted by another thread within a given wait time and the current thread is not interrupted, the lock is acquired. Boolean Trylock (long timeout, timeunit unit)//attempts to release this lock. void Unlock ()

Reentrantlock Example

By comparing "Example 1" and "Example 2", we can clearly understand the role of lock and unlock.

Example 1

 1 Import Java.util.concurrent.locks.Lock; 2 Import Java.util.concurrent.locks.ReentrantLock;        3 4//Locktest1.java 5//Warehouse 6 class Depot {7 private int size;        The actual number of warehouses 8 private lock lock; Exclusive lock 9 public Depot () {this.size = 0;12 This.lock = new Reentrantlock ();}14 IC void produce (int val) {lock.lock (); n try {size + = val;19 System.out.prin TF ("%s produce (%d)-size=%d\n", Thread.CurrentThread (). GetName (), Val, size), fin         Ally {Lock.unlock ();}24}25-public void consume (int val) {lock.lock (); 28                     try {size = val;30 System.out.printf ("%s consume (%d) <--size=%d\n", 31     Thread.CurrentThread (). GetName (), Val, size); 34} finally {Lock.unlock ();}35 }36}; 37 38//producer of the class Producer {privatE Depot depot;41 public Producer (Depot Depot) {this.depot = depot;44}45 46//Consumer products: Create a new thread to the silo The production of products in the library. Produce public void (final int val) {$ new Thread () {$ public void run () {D Epot.produce (val);}52}.start (); 53}54}55 56//Consumer (Customer) class Customer {+ + + Depot dep ot;59 public Customer (Depot Depot) {this.depot = depot;62}63 64//Consumer products: Create a new thread to consume the product from the warehouse. D-public void consume (final int val) {$ new Thread () {* * * void Run () {$ d Epot.consume (val);}70}.start ();}72}73, public class LockTest1 {n. public static VO         ID Main (string[] args) {Depot mdepot = new Depot (); "Producer" Mpro = new Producer (mdepot); 78 Customer MCus = new Customer (mdepot), Mpro.produce (), Bayi mpro.produce (Mcus.consume); (MCUS.C);Onsume (Mpro.produce) (110); 85}86} 

Operation result :

Thread-0 Produce ()--size=60thread-1 produce (+)--size=180thread-3 consume (<--size=30thread-2) Consume (<--size=-60thread-4 produce)--size=50

Results Analysis :
Depot is a warehouse. Through the produce () can produce goods in the warehouse, through the consume () can consume the goods in the warehouse. Exclusive lock lock allows for mutually exclusive access to the warehouse: The warehouse is locked through lock () before the goods are operated (in the production/consumption) warehouse, and then unlocked by unlock ().
(producer) is a producer class. Call the produce () function in producer to create a new thread to produce the product in the warehouse.
Customer is the consumer class. Calling the consume () function in customer can create a new product in a thread consumption warehouse.
(04) In main thread main, we will create a new 1 producer Mpro and create 1 new consumer MCUs. They produce/consume products separately from the warehouse.
According to the production/consumption quantity in Main, the final remaining product of the warehouse should be 50. The results of the operation are in line with our expectations!

There are two problems with this model:
(01) In reality, the capacity of the warehouse cannot be negative. However, the warehouse capacity in this model can be negative, which contradicts the reality!
(02) In reality, the capacity of the warehouse is limited. However, there is really no limit to the capacity in this model!
We'll talk a little bit about how to solve these two problems. Now, let's look at a simple example 2; by comparing "Example 1" and "Example 2", we can understand the use of lock (), unlock () more clearly.

Example 2

 1 Import Java.util.concurrent.locks.Lock; 2 Import Java.util.concurrent.locks.ReentrantLock;        3 4//Locktest2.java 5//Warehouse 6 class Depot {7 private int size;        The actual number of warehouses 8 private lock lock; Exclusive lock 9 public Depot () {this.size = 0;12 This.lock = new Reentrantlock ();}14 IC void produce (int val) {//Lock.lock (); +//try {size + = val;19 System.out.        printf ("%s produce (%d)-size=%d\n", Thread.CurrentThread (). GetName (), Val, size); 21//     } catch (Interruptedexception e) {$//} finally {//Lock.unlock (); 24//}25}26 27 public void consume (int val) {//Lock.lock ();//try {size-= val;31 System.        out.printf ("%s consume (%d) <--size=%d\n", Thread.CurrentThread (). GetName (), Val, size); 33// } finally {lock.unlock//(); 35//        }36}37}; 38 39//producer + class Producer {Depot depot;42 public Producer (Depot Depot) {This.depo t = depot;45}46 47//Consumer Products: Create a new thread to produce the product in the warehouse. Produce public void (final int val) {$ new Thread () {$ public void run () {Wuyi D Epot.produce (val);}53}.start (); 54}55}56 57//Consumer + class Customer {private Depot dep Ot;60 public Customer (Depot Depot) {this.depot = depot;63}64 65//Consumer Products: Create a new thread to consume the product from the warehouse. Consume public void (final int val) {new Thread () {() {()} () {D Epot.consume (val);}71}.start ();}73}74-public class LockTest2 {n-public static VO         ID Main (string[] args) {Depot mdepot = new Depot (); Producer Mpro = new Producer (mdepot); 79     Customer MCus = new Customer (mdepot); Mpro.produce (60); 82    Mpro.produce (+); Mcus.consume (Mcus.consume); Mpro.produce (110); 86}87} 

Run results (one time) :

Thread-0 Produce ()--size=-60thread-4 produce (+)--size=50thread-2 consume (all) <--size=-60thread-1 Produce (size=-60thread-3 consume) <--size=-60

Result Description :
Example 2 removes the lock lock on the basis of example 1. In Example 2, the final remaining product in the warehouse is-60, not the 50 we expect. The reason is that we did not implement mutually exclusive access to the warehouse.

Example 3

In Example 3, we solved two problems in example 1 by condition: "The capacity of the warehouse cannot be negative" and "the capacity of the warehouse is limited".
The problem is solved by condition. Condition is required to be used in conjunction with Lock: the await () method in condition allows the thread to block [similar to wait ()], and the wake-up thread [similar to notify ()] through the condition signal () method.

  1 Import Java.util.concurrent.locks.Lock;  2 Import Java.util.concurrent.locks.ReentrantLock;  3 Import java.util.concurrent.locks.Condition;    4 5//Locktest3.java 6//Warehouse 7 class Depot {8 private int capacity;        Capacity of the warehouse 9 private int size;        The actual number of warehouses is private lock lock;            Exclusive lock one private Condition fullcondtion;        Production conditions of the private Condition emptycondtion;         Consumption conditions: public Depot (int capacity) {this.capacity = capacity; this.size = 0; 17 This.lock = new Reentrantlock (); This.fullcondtion = Lock.newcondition (); This.emptycondtion = Lock.newcondition (); The public void produce (int val) {lock.lock (), and the try {//left means "want to live Production volume "(there is the possibility of producing too much, need more this production), int left = val; while (Left > 0) {28//Inventory is full, wait for "consumer" consumer products.              while (size >= capacity) 30       Fullcondtion.await (); 31//Get "Actual production quantity" (i.e. new quantity in stock) 32//If "inventory" + "quantity to produce" > "Total Capacity", then "actual increment" = "Total Capacity"-"current capacity". (Fills the warehouse at this time) 33//otherwise "actual increment" = "Quantity to be produced" Size+left int inc = () >capacity? (capacity-size): left; Size + = Inc; +-=-= Inc; PNS System.out.printf ("%s produce (%3d)--left=%3d, Inc=%3d, size=%3d\n", T Hread.currentthread (). GetName (), Val, left, Inc, size); 39//Notify "consumers" to consume. Emptycondtion.signal ();         (Interruptedexception e) {$} finally {Lock.unlock (); 45 } consume (int val) {lock.lock (); try {n//Left "Customer wants to consume quantity" (May consume too big, the stock is not enough, need this to spend more) int left = Val; (Left > 0) {54//stock is 0 o'clock, waiting for "producer" to produce products.                 55while (size <= 0) emptycondtion.await ();                 57//Get the "quantity actually consumed" (i.e. the quantity actually reduced in inventory) 58//If "inventory" < "quantity that the customer wants to consume", then "actual consumption" = "inventory"; 59 Otherwise, "actual consumption" = "Quantity to be consumed by the customer". int dec = (size<left)? Size:left; Size-= Dec; +-= Dec; System.out.printf ("%s consume (%3d) <--left=%3d, dec=%3d, size=%3d\n", + T Hread.currentthread (). GetName (), Val, left, Dec, size); Fullcondtion.signal ();         (Interruptedexception e) {Lock.unlock} () (70); }, the capacity public String toString () {The "+capacity+", Actual size: "+size;  75} 76}; 77 78//Producer-Class Producer {Depot Depot; Bayi, public Producer (Depot Depot) S.depot = depot; 84} 85 86//Consumer product: Create a new thread to produce the product in the warehouse. 87    public void produce (final int val) {The new Thread () {The "public void" run () {$ d Epot.produce (Val); }.start (); 93} 94} 95 96//Consumer class Customer {98 private Depot Depot; the public customer (Depot Depot) {1 This.depot = depot;102}103 104//Consumer product: Create a new thread to consume the product from the warehouse.                 Consume public void-(final int val) {106 New Thread () {107 public void Run () {108 Depot.consume (val); 109}110}.start (); 111}112}113 the public class LockTest3 {Publi c static void Main (string[] args) {Depot mdepot = new Depot (+); 117 Producer Mpro = new Producer (MD         Epot) 118 Customer MCus = new Customer (mdepot); 119 Mpro.produce 121 (120); 122 Mcus.consume (123 mcus.consume); 124 mpro.produce (110); 125}126}

Run results (one time) :

Thread-0 Produce ()--left=  0, inc=, size= 60thread-1 Produce (+)--left=, inc=, size=100thread- 2 Consume (<--) left=  0, dec=, size= 10thread-3 consume (<--left=140, dec=, size= 0thread-4  PR Oduce ()--left=, inc=100, size=100thread-3 consume (All) <--left=, dec=100, size=  0thread-4 Produce (1 --left=  0, inc=, size= 10thread-3 consume (<--left=), dec=, size= 0thread-1  Produce (120) --left=  0, inc=, size= 80thread-3 consume () <--left=  0, dec=, size= 50

Java Lock--reentrantlock

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.