A problem about Java multithreading

Assume the following courses

public class TestObject{
    public void synchronized method1(){
        //some 1000 lines of code
    }

    public void method2(){
        //some 1000 lines of code
    }
}

Suppose two threads access the same testobject class instance, let's call them T1 and T2 I want to know what happens in the following scenarios

>When T1 is in the middle of accessing method1() Now T2 trying to access method2(). > When T1 is in the middle of accessing method2() Now T2 trying to access method1()

My understanding is that for the first problem, thread T2 will not be granted permission because the object will be locked by T1 For the second problem, thread T2 will be granted access and lock the object and stop T1 from execution But my assumption is wrong Who can explain?

thank you

Solution

When declaring a method to synchronize, for example:

public synchronized void foo() {
    // Do something
}

The compiler sees it as something you wrote:

public void foo() {
    synchronized (this) {
        // Do something
    }
}

In your example, you have a synchronous method and an asynchronous method This means that only access to method 1 will be locked The lock check is completed only when the synchronization block is entered, so calling method2 does not trigger any lock

In order to answer your two questions, in both cases, both threads will be allowed to continue because they do not attempt to obtain a lock on the same object If you declare method 2 to be synchronized (or manually add a synchronization block), you force one thread to wait for another thread

Remember that synchronizing an object does not prevent other threads from calling methods on the object It only prevents another thread from entering a synchronization block with the same lock object

Incidentally, it's usually better to have an internally locked object than to declare a method to synchronize, for example,

class Foo {
    private final Object LOCK = new Object();
    public void doSomething() {
        synchronized (LOCK) {
            // Whatever
        }
    }
}

Otherwise, I can break your thread safety by doing this:

class MessEverythingUp {
    public MessEverythingUp(Foo foo) {
        synchronized (foo) {
            while (true) {
                System.out.println("Pwnd ur thread safety");
            }
        }
    }
}

Because I am locking the instance of foo, your synchronized method (with implicit "synchronized (this)") will not get locked and will be permanently blocked Most importantly, you can't stop this because I can sync any object I like Obviously, this example is extreme, but if you are not careful about this kind of thing, you may get annoying, subtle deadlock errors

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>