Fundamentals 16 min read

Can Threads Run Two Synchronized Methods Together? synchronized vs ReentrantLock

This article examines whether multiple threads can simultaneously invoke two synchronized methods within the same class, comparing Java's intrinsic synchronized lock with the explicit ReentrantLock, and demonstrates through various code scenarios how object locks and lock instances affect concurrent execution.

Java Interview Crash Guide
Java Interview Crash Guide
Java Interview Crash Guide
Can Threads Run Two Synchronized Methods Together? synchronized vs ReentrantLock

1. synchronized

1. Multiple threads accessing two synchronized methods of the same class instance:

package synchronizedTest;

public class Example1 {
    private int num = 0 ;
    // getters/setters omitted
    public synchronized void method1() {
        System.out.println("同步方法1进入");
        for(int i = 0 ; i<10 ; i++) {
            System.out.print("同步方法1:"+num+"--");
            num++ ;
        }
        System.out.println("同步方法1结束");
    }
    public synchronized void method2() {
        System.out.println("method2进入:");
        for(int i = 0 ; i<10 ; i++) {
            System.out.print("method2:"+num+"--");
            num++ ;
        }
        System.out.println("method2结束");
    }
    public static void main(String[] args) {
        final Example1 example1 = new Example1();
        Thread thread1 = new Thread(new Runnable() {
            @Override
            public void run() {
                example1.method1();
            }
        });
        Thread thread2 = new Thread(new Runnable() {
            @Override
            public void run() {
                example1.method2();
            }
        });
        try {
            thread2.join();
            thread1.join();
            thread1.start();
            thread2.start();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

Output:

method1进入
同步方法1:0--同步方法1:1--同步方法1:2--同步方法1:3--同步方法1:4--同步方法1:5--同步方法1:6--同步方法1:7--同步方法1:8--同步方法1:9--method1结束
method2进入:
method2:10--method2:11--method2:12--method2:13--method2:14--method2:15--method2:16--method2:17--method2:18--method2:19--method2结束

Clearly the threads cannot simultaneously access the two synchronized methods of the same instance.

2. Multiple threads accessing two synchronized methods of different class instances:

Modify the main method to create a second instance and let the second thread call method2 on it.

final Example1 example2 = new Example1();
Thread thread2 = new Thread(new Runnable() {
    @Override
    public void run() {
        example2.method2();
    }
});

Output:

同步方法1进入
method2进入:
method2:0--method2:1--同步方法1:0--同步方法1:1--同步方法1:2--method2:2--同步方法1:3--method2:3--同步方法1:4--method2:4--同步方法1:5--method2:5--同步方法1:6--同步方法1:7--method2:6--同步方法1:8--同步方法1:9--method2:7--同步方法1结束
method2:8--method2:9--method2结束

Now the threads can access the two methods concurrently because they operate on different instances.

3. Multiple threads accessing two Runnable run() methods synchronized on synchronized(this) :

package synchronizedTest;

public class Example2 {
    private int num ;
    public Runnable runnable1 = new Runnable() {
        @Override
        public void run() {
            synchronized (this) {
                System.out.println("线程1进入");
                for(int i = 0 ; i < 10 ; i++) {
                    System.out.print("线程1:"+num+"--");
                }
                System.out.println("线程1结束");
            }
        }
    };
    public Runnable runnable2 = new Runnable() {
        @Override
        public void run() {
            synchronized (this) {
                System.out.println("thread2进入");
                for(int i = 0 ; i < 10 ; i++) {
                    System.out.print("thread2:"+num+"--");
                }
                System.out.println("thread2结束");
            }
        }
    };
    public static void main(String[] args) {
        Example2 example = new Example2();
        new Thread(example.runnable1).start();
        new Thread(example.runnable2).start();
    }
}

Output shows that both run methods can execute concurrently because each synchronized block locks on a different this (the anonymous Runnable instance).

2. ReentrantLock

1. Multiple threads accessing two synchronized methods of the same class instance:

package ReentrantLockTest;

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

public class LockExample {
    private int num;
    private Lock lock = new ReentrantLock();
    public void method1() {
        lock.lock();
        System.out.println("同步方法1进入");
        for(int i = 0 ; i<10 ; i++) {
            System.out.print("同步方法1:"+num+"--");
            num++ ;
        }
        System.out.println("同步方法1结束");
        lock.unlock();
    }
    public void method2() {
        lock.lock();
        System.out.println("method2进入:");
        for(int i = 0 ; i<10 ; i++) {
            System.out.print("method2:" + num + "--");
            num++;
        }
        System.out.println("method2结束");
        lock.unlock();
    }
    public static void main(String[] args) {
        final LockExample example = new LockExample();
        Thread thread1 = new Thread(() -> example.method1());
        Thread thread2 = new Thread(() -> example.method2());
        try {
            thread2.join();
            thread1.join();
            thread1.start();
            thread2.start();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

Output shows that the threads cannot access the two methods concurrently, just like with synchronized.

2. Multiple threads accessing two synchronized methods of different class instances:

public static void main(String[] args) {
    final LockExample example1 = new LockExample();
    final LockExample example2 = new LockExample();
    Thread thread1 = new Thread(() -> example1.method1());
    Thread thread2 = new Thread(() -> example2.method2());
    // start threads as before
}

Output demonstrates that when each thread uses a different instance (and thus a different ReentrantLock object), they can run concurrently.

3. Multiple threads accessing two Runnable run() methods synchronized with ReentrantLock:

package ReentrantLockTest;

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

public class Lockexample2 {
    private int num;
    private Lock lock = new ReentrantLock();
    public Runnable runnable1 = () -> {
        lock.lock();
        System.out.println("线程1进入");
        for(int i=0;i<10;i++) {
            System.out.print("线程1:"+num+"--");
        }
        System.out.println("线程1结束");
        lock.unlock();
    };
    public Runnable runnable2 = () -> {
        lock.lock();
        System.out.println("thread2进入");
        for(int i=0;i<10;i++) {
            System.out.print("thread2:"+num+"--");
        }
        System.out.println("thread2结束");
        lock.unlock();
    };
    public static void main(String[] args) {
        Lockexample2 example = new Lockexample2();
        new Thread(example.runnable1).start();
        new Thread(example.runnable2).start();
    }
}

Because both runnables share the same ReentrantLock instance, the second thread must wait for the first to release the lock, so they do not run concurrently.

If two separate instances of Lockexample2 are created, each holds its own ReentrantLock, allowing concurrent execution.

3. Conclusion

Revisiting the original question: can multiple threads simultaneously invoke two synchronized methods in a class?

For synchronized :

Two synchronized methods in the same instance cannot be executed concurrently.

Two synchronized methods in different instances can be executed concurrently.

If the synchronization is on synchronized(this) inside Runnable run() methods, the locks are on distinct Runnable objects, so the methods can run concurrently regardless of instance.

For ReentrantLock :

Two methods protected by the same ReentrantLock (same instance) cannot run concurrently, whether they are ordinary methods or run() methods.

Two methods protected by different ReentrantLock objects (different class instances) can run concurrently.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

javaSynchronizationReentrantLocksynchronized
Java Interview Crash Guide
Written by

Java Interview Crash Guide

Dedicated to sharing Java interview Q&A; follow and reply "java" to receive a free premium Java interview guide.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.