当前位置:网站首页>5 locksupport and thread interruption

5 locksupport and thread interruption

2022-06-13 11:58:00 It rains when the wind blows

5 LockSupport With thread interrupts

Catalog

Thread interrupt mechanism

Ali ant financial interview questions

 Insert picture description here

voidinterrupt() Interrupt this thread
static booleaninterrupted() Tests whether the current thread has been interrupted
booleanisInterrupted() Test whether this thread has been interrupted
  • Have you understood the three methods ? Where to use it ?

  • How to stop a running thread ?

  • How to interrupt a running thread ??

What is interrupt mechanism ?

  • First

A thread should not be forced to interrupt or stop by other threads , It should be stopped by the thread itself .

therefore ,Thread.stop, Thread.suspend, Thread.resume It's been abandoned .

  • secondly

stay Java There is no way to stop a thread immediately , However, stopping threads is particularly important , For example, cancel a time-consuming operation .

therefore ,Java Provides a method for stopping threads Consultation mechanism —— interrupt .

Interruption is just a collaborative negotiation mechanism ,Java No syntax added to interrupt , The interruption process needs to be implemented by the programmer himself .

To interrupt a thread , You need to manually call the thread's interrupt Method , This method only sets the interrupt ID of the thread object to true;

Then you need to write your own code to constantly detect the identification bit of the current thread , If true, Indicates that another thread requests this thread to interrupt ,

What to do at this time requires you to write your own code to realize .

There is an identity in each thread object , Used to indicate whether a thread is interrupted ; The identification bit is true To interrupt , by false Means not interrupted ;

By calling the interrupt Method to set the identification bit of the thread to true; Can be invoked in other threads , You can also call it in your own thread .

  • eg. Customers smoke in smoke-free restaurants , The waiter wanted him to stop smoking , Not to force him to stop smoking , Instead, he marked his sign as true, Specifically, customers should stop smoking by themselves .( It embodies the negotiation mechanism )

Interrupt correlation API Description of the three methods

 Insert picture description here

public void interrupt() Example method , Example method interrupt() Just set the interrupt status of the thread to true, Initiate a negotiation without immediately stopping the thread
public static boolean interrupted() Static methods ,Thread.interrupted(); Determine whether the thread is interrupted , And clear the current interrupt state Two things :1 Returns the interrupt status of the current thread 2 Set the interrupt status of the current thread to false( This method is a little difficult to understand , Because the results of two consecutive calls may be different .)
public boolean isInterrupted() Example method , Determine whether the current thread is interrupted ( Check the interrupt flag bit )

Interview questions of Dachang : How to use interrupt ID to stop thread ?

1 How to stop interrupting a running thread ?

① Through one volatile Variable implementation

  • volatile Guaranteed visibility ,t2 After modifying the flag bit, it can be t1 notice
public class interruptDemo {
    
    static volatile boolean isStop = false;

    public static void main(String[] args) {
    
        new Thread(()->{
    
            while(true){
    
                if(isStop){
    // If this flag bit is changed by another thread to true 了 
                    System.out.println(Thread.currentThread().getName()+"\t isStop Changed to true, Termination of procedure ");
                    break;
                }
                System.out.println("t1 ------hello volatile");//---------------------- If it doesn't stop , Then keep printing 
            }
        },"t1").start();

        try {
    TimeUnit.MILLISECONDS.sleep(20);} catch (InterruptedException e) {
    e.printStackTrace();}

        new Thread(()->{
    
            isStop = true;
        },"t2").start();
    }
}
//--
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 isStop Changed to true, Termination of procedure 

② adopt AtomicBoolean( Atomic Boolean )

public class interruptDemo {
    

    static AtomicBoolean atomicBoolean = new AtomicBoolean(false);

    public static void main(String[] args) {
    
        m1_volatile();
    }

    public static void m1_volatile() {
    
        new Thread(()->{
    
            while(true){
    
                if(atomicBoolean.get()){
    // If this flag bit is changed by another thread to true 了 
                    System.out.println(Thread.currentThread().getName()+"\t isStop Changed to true, Termination of procedure ");
                    break;
                }
                System.out.println("t1 ------hello volatile");//---------------------- If it doesn't stop , Then keep printing 
            }
        },"t1").start();

        try {
    TimeUnit.MILLISECONDS.sleep(20);} catch (InterruptedException e) {
    e.printStackTrace();}

        new Thread(()->{
    
            atomicBoolean.set(true);
        },"t2").start();
    }
}
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 ------hello volatile
//t1 isStop Changed to true, Termination of procedure 

③ adopt Thread Class has its own interrupt api Method realization

    // The default interrupt flag bit is false, Then it was changed to true
    public static void main(String[] args) {
    
        m1_volatile();
    }

    public static void m1_volatile() {
    
        Thread t1 = new Thread(() -> {
    
            while (true) {
    
                if (Thread.currentThread().isInterrupted()) {
    // Once the interrupt flag bit is found to be modified 
                    System.out.println(Thread.currentThread().getName() + "\t isInterrupted() Changed to true, Termination of procedure ");
                    break;
                }
                System.out.println("t1 ------hello interrupt ");//---------------------- If it doesn't stop , Then keep printing 
            }
        }, "t1");
        t1.start();

        try {
    TimeUnit.MILLISECONDS.sleep(20);} catch (InterruptedException e) {
    e.printStackTrace();}

        new Thread(()->{
    
            t1.interrupt();// hold t1 interrupt 
        },"t2").start();
    }
}

//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 ------hello interrupt 
//t1 isInterrupted() Changed to true, Termination of procedure 

—API Source code analysis

Example method interrupt(), no return value

//Thread.java
public void interrupt() {
    
        if (this != Thread.currentThread())
            checkAccess();

        synchronized (blockerLock) {
    
            Interruptible b = blocker;
            if (b != null) {
    
                interrupt0();           // Just to set the interrupt flag---- Called interrupt0() Method 
                b.interrupt(this);
                return;
            }
        }
        interrupt0();
    }
//Thread.java
    /* Some private helper methods */
    private native void setPriority0(int newPriority);
    private native void stop0(Object o);
    private native void suspend0();
    private native void resume0();
    private native void interrupt0();  //--------------------------- Called c Bottom 
    private native void setNativeName(String name);

Example method isInterrupted, Returns a Boolean value

    //Thread.java
    public boolean isInterrupted() {
    
        return isInterrupted(false);
    }
    //Thread.java
    private native boolean isInterrupted(boolean ClearInterrupted);// Also called c Bottom 

explain

  • say concretely , When it comes to a thread , call interrupt() when :

    1. If the thread is in Normal active state , The thread's interrupt flag will be set to true, That's it . The thread with interrupt flag will continue to run normally , Unaffected . therefore , interrupt() It doesn't really interrupt threads , You need to cooperate with the called thread .

    2. ② If the thread is blocked ( For example, in the sleep, wait, join Equal state ), To call the current thread object in another thread interrupt Method , So the thread will Immediately exit the blocked state ( The interrupt state will be cleared ), And throw a InterruptedException abnormal .

    3. Interrupt inactivity The thread of Can't Any impact , Take a look at the following case )

2 The interrupt ID of the current thread is true, Does the thread stop immediately ?

  • no

    • Only one interrupt state is set
  • See if the interrupt will stop this immediately 300 The thread of

    • no , Although the interrupt flag bit has changed . however i It's been circulating
public class InterruptDemo02 {
    
    public static void main(String[] args) {
    
        Thread t1 = new Thread(()->{
    
            for(int i = 0;i < 300;i ++){
    
                System.out.println("---------" + i);
            }
            System.out.println("after t1.interrupt()--- The first 2 Time ----"+Thread.currentThread().isInterrupted());
        },"t1");
        t1.start();
        System.out.println("before t1.interrupt()----"+t1.isInterrupted());
        t1.interrupt();
        try {
    TimeUnit.MILLISECONDS.sleep(3);} catch (InterruptedException e) {
    e.printStackTrace();}
        System.out.println("after t1.interrupt()--- The first 1 Time ---"+t1.isInterrupted());
        try {
    TimeUnit.MILLISECONDS.sleep(3000);} catch (InterruptedException e) {
    e.printStackTrace();}
        System.out.println("after t1.interrupt()--- The first 3 Time ---"+t1.isInterrupted());
    }
}
//before t1.interrupt()----false
//---------0
//---------1
//---------2
//---------3
//....
//---------136
//after t1.interrupt()--- The first 1 Time ---true ------ The interrupt flag bit here is set to true, however t1 Still running 
//---------137
//---------298
//---------299
//after t1.interrupt()--- The first 2 Time ----true
//after t1.interrupt()--- The first 3 Time ---false// Interrupting an inactive thread does not have any effect , After the thread ends, it should automatically change to false

Follow up cases - thorough

  • On the skeleton of our basic interrupt program + One sleep Blocking

  • Interrupt exception And Will cause the program to loop indefinitely .

public class InterruptDemo03 {
    
    public static void main(String[] args) {
    
        Thread t1 =  new Thread(()->{
    
            while(true){
    
                if(Thread.currentThread().isInterrupted()){
    
                    System.out.println(Thread.currentThread().getName()+"\t"+
                            " Interrupt flag bit :"+Thread.currentThread().isInterrupted()+" Termination of procedure ");
                    break;
                }
                try {
    
                    Thread.sleep(200);
                } catch (InterruptedException e) {
    
                    e.printStackTrace();
                    // Thread.currentThread().interrupt();  If you add this , The program can be terminated , It will only explode abnormally 
                }
                System.out.println("-----hello InterruptDemo03");
            }
        },"t1");
        t1.start();
        try {
    TimeUnit.MILLISECONDS.sleep(1);} catch (InterruptedException e) {
    e.printStackTrace();}
        new Thread(() -> t1.interrupt()).start();
    }
}
// The explosion is abnormal , And the program has been running 
//java.lang.InterruptedException: sleep interrupted
// at java.lang.Thread.sleep(Native Method)
//-----hello InterruptDemo03
//-----hello InterruptDemo03
//-----hello InterruptDemo03
//......
//----------------------------
//--------- added Thread.currentThread().interrupt();
//java.lang.InterruptedException: sleep interrupted
// at java.lang.Thread.sleep(Native Method)
// at com.zhang.admin.controller.InterruptDemo03.lambda$main$0(InterruptDemo03.java:15)
// at java.lang.Thread.run(Thread.java:748)
//-----hello InterruptDemo03
//t1  Interrupt flag bit :true Termination of procedure 


  • above

    1. ② If the thread is blocked ( For example, in the sleep, wait, join Equal state ), To call the current thread object in another thread interrupt Method , So the thread will Immediately exit the blocked state ( The interrupt state will be cleared ), And throw a InterruptedException abnormal .
/** * 1  Interrupt flag bit   The default is false * 2 t2 ----->t1 An interrupt negotiation was issued ,t2 call t1.interrupt(), Interrupt flag bit true * 3  Interrupt flag bit true, Under normal circumstances , The program to stop ,^-^ * 4  Interrupt flag bit true, Under abnormal conditions ,InterruptedException, Will clear the interrupt state , And will receive InterruptedException. Interrupt flag bit false Cause infinite loop . * * 5  stay catch In block , The interrupt flag bit needs to be set to again true,2 Call stop  */
sleep Method throw InterruptedException after , The interrupt flag is also cleared to false, We are catch Don't pass th.interrupt() Method again sets the interrupt flag to true, This leads to infinite loops 

A small summary

  • Interruption is just a collaborative mechanism , Modifying the interrupt flag bit is nothing more , Not immediately stop interrupt

3 Static methods Thread.interrupted(), Talk about your understanding

  • api The second one in

    • public static boolean interrupted()
    • Static methods ,Thread.interrupted(); Determine whether the thread is interrupted , And clear the current interrupt state Two things :1 Returns the interrupt status of the current thread 2 Set the interrupt status of the current thread to false( This method is a little difficult to understand , Because the results of two consecutive calls may be different .) |
public class InterruptDemo04 {
    
    public static void main(String[] args) {
    
        System.out.println(Thread.currentThread().getName()+"\t"+Thread.interrupted());
        System.out.println(Thread.currentThread().getName()+"\t"+Thread.interrupted());
        System.out.println("-----1");
        Thread.currentThread().interrupt();// The interrupt flag bit is set to true
        System.out.println("-----2");
        System.out.println(Thread.currentThread().getName()+"\t"+Thread.interrupted());
        System.out.println(Thread.currentThread().getName()+"\t"+Thread.interrupted());
    }
}
//main false
//main false
//-----1
//-----2
//main true
//main false
  • Look at the source ,interrupted() contrast isInterrupted()

    public static boolean interrupted() {
          
            return currentThread().isInterrupted(true);
        }
        
    private native boolean isInterrupted(boolean ClearInterrupted);
    
    public boolean isInterrupted() {
          
            return isInterrupted(false);
        }
    
    private native boolean isInterrupted(boolean ClearInterrupted);
    
    
    • They all call at the bottom native Method isInterrupted.

    • Just pass in the parameters ClearInterrupted A pass on parameter passed on true, One by one false.

      • Static methods interrupted() in true Indicates that the current interrupt state is cleared .

      • Example method isInterrupted Will not be .

LockSupport What is it?

  • Official explanation : Basic thread blocking primitives for creating locks and other synchronization classes .

    [ Failed to transfer the external chain picture , The origin station may have anti-theft chain mechanism , It is suggested to save the pictures and upload them directly (img-PyfrOAqO-1654754693266)(image/image_SOr3KJQSy_.png)]

  • The core Namely park() and unpark() Method

    • park() The method is Blocking threads

    • unpark() The method is Unblock threads
       Please add a picture description

Thread waiting wake-up mechanism

3 Ways to let threads wait and wake up

  1. Use Object Medium wait() Method to make the thread wait , Use Object Medium notify() Method wake up thread

  2. Use JUC In bag Condition Of await() Method to make the thread wait , Use signal() Method wake up thread

  3. LockSupport Class can block the current thread and wake up the specified blocked thread
     Insert picture description here

①Object Class wait and notify Method to realize thread waiting and wake-up

  • normal

    public class LockSupportDemo
    {
          
        public static void main(String[] args)
        {
          
            Object objectLock = new Object();
    
            new Thread(() -> {
          
                synchronized (objectLock) {
          
                    System.out.println(Thread.currentThread().getName()+"\t ---- come in");
                    try {
          
                        objectLock.wait();//---------------------- Let him wait here first 
                    } catch (InterruptedException e) {
          
                        e.printStackTrace();
                    }
                }
                System.out.println(Thread.currentThread().getName()+"\t"+"--- Wake up ");
            },"t1").start();
    
            // Pause the thread for a few seconds 
            try {
           TimeUnit.SECONDS.sleep(3L); } catch (InterruptedException e) {
           e.printStackTrace(); }
    
            new Thread(() -> {
          
                synchronized (objectLock) {
          
                    objectLock.notify();//------------------------- Wake it up again 
                    System.out.println(Thread.currentThread().getName()+"\t --- A notice ");
                }
            },"t2").start();
        }
    }
    //t1 ---- come in
    //t2 --- A notice 
    //t1 --- Wake up 
    
  • abnormal 1— Get rid of synchronized

    • Explain to use wait and notify Must be added synchronized
    public class LockSupportDemo
    {
          
        public static void main(String[] args)
        {
          
            Object objectLock = new Object();
    
            new Thread(() -> {
          
            // synchronized (objectLock) {
          
                    System.out.println(Thread.currentThread().getName()+"\t ---- come in");
                    try {
          
                        objectLock.wait();
                    } catch (InterruptedException e) {
          
                        e.printStackTrace();
                    }
          // }
                System.out.println(Thread.currentThread().getName()+"\t"+"--- Wake up ");
            },"t1").start();
    
            // Pause the thread for a few seconds 
            try {
           TimeUnit.SECONDS.sleep(3L); } catch (InterruptedException e) {
           e.printStackTrace(); }
    
            new Thread(() -> {
          
           // synchronized (objectLock) {
          
                    objectLock.notify();
                    System.out.println(Thread.currentThread().getName()+"\t --- A notice ");
           // }
            },"t2").start();
        }
    }
    //t1 ---- come in
    //Exception in thread "t1" java.lang.IllegalMonitorStateException
    // at java.lang.Object.wait(Native Method)
    // at java.lang.Object.wait(Object.java:502)
    // at com.zhang.admin.controller.LockSupportDemo.lambda$main$0(LockSupportDemo.java:15)
    // at java.lang.Thread.run(Thread.java:748)
    
  • abnormal 2— hold notify and wait The execution sequence of is reversed

    • The order of instructions cannot be reversed
    public class LockSupportDemo
    {
          
        public static void main(String[] args)
        {
          
            Object objectLock = new Object();
    
            new Thread(() -> {
          
                try {
           TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) {
           e.printStackTrace(); }
                synchronized (objectLock) {
          
                    System.out.println(Thread.currentThread().getName()+"\t ---- come in");
                    try {
          
                        objectLock.wait();
                    } catch (InterruptedException e) {
          
                        e.printStackTrace();
                    }
                }
                System.out.println(Thread.currentThread().getName()+"\t"+"--- Wake up ");
            },"t1").start();
    
    
    
            new Thread(() -> {
          
                synchronized (objectLock) {
          
                    objectLock.notify();// This is done first 
                    System.out.println(Thread.currentThread().getName()+"\t --- A notice ");
                }
            },"t2").start();
        }
    }
    // Has been in a cycle 
    

A small summary

  • wait and notify The method must be in Sync In a block or method , And Pair Appear to use

  • First wait after notify only OK, The order

②Condition Interface await after signal Method to realize thread waiting and wake-up

  • normal

    public class LockSupportDemo
    {
          
        public static void main(String[] args)
        {
          
            Lock lock = new ReentrantLock();
            Condition condition = lock.newCondition();
    
            new Thread(() -> {
          
                lock.lock();
                try
                {
          
                    System.out.println(Thread.currentThread().getName()+"\t-----come in");
                    condition.await();
                    System.out.println(Thread.currentThread().getName()+"\t ----- Awakened ");
                } catch (InterruptedException e) {
          
                    e.printStackTrace();
                } finally {
          
                    lock.unlock();
                }
            },"t1").start();
    
            // Pause the thread for a few seconds 
            try {
           TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) {
           e.printStackTrace(); }
    
            new Thread(() -> {
          
                lock.lock();
                try
                {
          
                    condition.signal();
                } catch (Exception e) {
          
                    e.printStackTrace();
                } finally {
          
                    lock.unlock();
                }
                System.out.println(Thread.currentThread().getName()+"\t"+" I want to wake up ");
            },"t2").start();
    
        }
    }
    //t1 -----come in
    //t2  I want to wake up 
    //t1 ----- Awakened 
    
  • abnormal 1 The principle of same

    • Still back IllegalMonitorStateException
  • abnormal 2 The principle of same

    • It's still going round and round

A small summary

  • await and notify Similar to the above wait and notify

    • Condition Thread waiting and wakeup methods in , You need to acquire the lock first

    • Be sure to await after signal, It can't be reversed

Object and Condition Restrictions on use

  • summary

    • The thread must first acquire and hold the lock , Must be in the lock block (synchronized or lock) in

    • You have to wait before you wake up , Thread can be awakened

③LockSupport Class park Waiting and unpark Wake up the

What is it?

  • adopt park() and unpark(thread) Method to block and wake up threads

  • Website to explain

    [ Failed to transfer the external chain picture , The origin station may have anti-theft chain mechanism , It is suggested to save the pictures and upload them directly (img-za4dJOuv-1654754693269)(image/image_E5vM4GxxSB.png)]

    • LockSupport Is the basic thread blocking primitive used to create locks and other synchronization classes .

    • LockSupport Class uses a method called Permit( The license ) To block and wake up threads , Each thread has a license (permit),

    • permit( The license ) There are only two values 1 and 0, The default is 0.0 It's blocking ,1 It's wake up

    • You can think of licensing as a kind of (0,1) Semaphore (Semaphore), But with Semaphore The difference is , The cumulative upper limit of the license is 1.

The license (Permit)

The main method

API

 Insert picture description here

Blocking

  • park()/park(Object blocker)

  • call LockSupport.park() when , Found that it called unsafe class , And by default, it passes a 0

    public static void park() {
          
            UNSAFE.park(false, 0L);
        }
    

 Insert picture description here

  • permit The default is zero , So at the beginning of the call park() Method , The current thread will block , Until another thread will permit Set to 1 when ,park Method will be awakened ,
    Then it will permit Set to zero again and return .

Wake up the

  • call LockSupport.unpark(); when , Also called unsafe class

    public static void unpark(Thread thread) {
          
            if (thread != null)
                UNSAFE.unpark(thread);
        }
    

 Insert picture description here

  • call unpark(thread) After the method , Will be thread Permission for threads permit Set to 1( Note multiple calls unpark Method , Not cumulative ,permit Value or 1) Will wake up automatically thread Threads , That is, in the previous blocking LockSupport.park() Method will immediately return .

Code

  • normal + No lock block requirements

    public class LockSupportDemo
    {
          
        public static void main(String[] args) {
          
            Thread t1 = new Thread(()->{
          
                System.out.println(Thread.currentThread().getName()+"\t----------come in");
                LockSupport.park();
                System.out.println(Thread.currentThread().getName()+"\t---------- Wake up ");
            },"t1");
            t1.start();
    
            new Thread(()->{
          
                LockSupport.unpark(t1);
                System.out.println(Thread.currentThread().getName()+"\t----- A notice , To wake up t1");
            },"t2").start();
        }
    }
    //t1 ----------come in
    //t2 ----- A notice , To wake up t1
    //t1 ---------- Wake up 
    
  • The previous error wakes up first and then waits ,LockSupport Still support

    public class LockSupportDemo
    {
          
        public static void main(String[] args) {
          
            Thread t1 = new Thread(()->{
          
                try {
          TimeUnit.SECONDS.sleep(3);} catch (InterruptedException e) {
          e.printStackTrace();}
                System.out.println(Thread.currentThread().getName()+"\t----------come in"+"\t"+System.currentTimeMillis());
                LockSupport.park();
                System.out.println(Thread.currentThread().getName()+"\t---------- Wake up "+"\t"+System.currentTimeMillis());
            },"t1");
            t1.start();
    
            new Thread(()->{
          
                LockSupport.unpark(t1);
                System.out.println(Thread.currentThread().getName()+"\t----- A notice , To wake up t1");
            },"t2").start();
        }
    }
    //t2 ----- A notice , To wake up t1
    //t1 ----------come in 1654750785663
    //t1 ---------- Wake up  1654750785663
    

    sleep Method 3 Wake up in seconds , perform park Invalid , No blocking effect , Explain the following . First executed. unpark(t1) Cause the above park The method is null and void , Time is the same
    - Similar to the highway ETC, Bought the pass in advance unpark, Lift the handrail directly at the gate and let it go , No, park Intercepted .

  • In pairs, remember

Last

  • There is only one license

    public class LockSupportDemo
    {
          
        public static void main(String[] args) {
          
            Thread t1 = new Thread(()->{
          
                try {
          TimeUnit.SECONDS.sleep(3);} catch (InterruptedException e) {
          e.printStackTrace();}
                System.out.println(Thread.currentThread().getName()+"\t----------come in"+"\t"+System.currentTimeMillis());
                LockSupport.park();
                LockSupport.park();
                System.out.println(Thread.currentThread().getName()+"\t---------- Wake up "+"\t"+System.currentTimeMillis());
            },"t1");
            t1.start();
    
            new Thread(()->{
          
                LockSupport.unpark(t1);
                LockSupport.unpark(t1);
                System.out.println(Thread.currentThread().getName()+"\t----- A notice , To wake up t1");
            },"t2").start();
        }
    }
    //t2 ----- A notice , To wake up t1
    //t1 ----------come in 1654750970677-------------------- It's stuck here 
    
  • A small summary

    Lock Support Is the basic thread blocking primitive used to create locks and other synchronization classes .
    Lock Support Is a thread blocking tool class , All methods are static , The thread can be blocked at any location , There is a corresponding wake-up method after blocking . Root knot
    At the end of , Lock Support Called Unsafe Medium native Code .

    Lock Support Provide park() and unpark() Method realization Blocking threads and Unblock threads The process of
    Lock Support And every thread that uses it has a license (permit) relation .
    Each thread has an associated permit, permit At most one , Repeated calls to un park And they don't accumulate credentials .

    The understanding of image
    Thread blocking requires consuming credentials (permit) , This certificate is at most 1 individual .
    When calling When the method is used
    * If there is a certificate , It will consume the voucher directly and exit normally ;
    * If there is no certificate , You have to block and wait for credentials to be available ;
    and **** On the contrary , It will add a voucher , But the certificate can only have at most
    1
    individual , Accumulation is invalid .

Interview questions

  • Why can we break through wait/notify The original calling sequence of ?
    because un park Got a certificate , Call later park Method , You can have the right voucher consumption , So it won't block .
    After the vouchers are issued first, they can be unblocked later .

  • Why wake up twice and block twice , But the end result will also block the thread ?
    Because the maximum number of vouchers is 1, Two consecutive calls un park And call once un park The effect is the same , Only one voucher will be added ;
    And call twice park But you need to consume two vouchers , Not enough proof , No release .

原网站

版权声明
本文为[It rains when the wind blows]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/164/202206131147398545.html