简体   繁体   中英

Confusion Regarding java threads on same/different objects

public class Computation extends Thread {

    private int num;
    private boolean isComplete;

    public Computation(int nu) {
        num = nu;
    }

    public void run() {
        System.out.println("Thread Called is: " + Thread.currentThread().getName());
    }

    public static void main(String... args) {
        Computation [] c = new Computation[4];
        for (int i = 0; i < 3; i++) {
            c[i] = new Computation(i);
            c[i].start();
        }
    }
}

My Question is in main function we are creating every time a new Computation object on which the thread is being started then why we need to snchrnoized the run method? As we know for every different class object 'this' reference is different so we don't need to synchronize.

Also in another Example:

public class DiffObjSynchronized implements Runnable {

    @Override
    public void run() {
        move(Thread.currentThread().getId());           
    }

    public synchronized void move(long id) {
        System.out.print(id + " ");
        System.out.print(id + " ");
    }

    public static void main(String []args) {
        DiffObjSynchronized a = new DiffObjSynchronized();
        /**** output ****/
        // 8    9   8   9
        new Thread(a).start();
        new Thread(new DiffObjSynchronized()).start();
    }
}

Here is second example just like first we create a Thread on 2 different instances of class. Here we synchronize the move() method but by definition: "two different objects can enter the synchronized method at the same time"

Please share your feedback?

Your threads are operating on different objects since you create a new instance for each thread. The intrinsic lock used by synchronized belongs to the instance. So the synchronized methods entered by your threads are guarded by different locks.

If I understand you correctly, your question is: "Why is the move method synchronized?"

The answer is: it shouldn't be, for two reasons:

  1. It doesn't access any fields, so there is nothing that could be corrupted by having many threads inside that method at once.

  2. Each thread gets a different instance of the object, and thus a different lock. So the synchronized modifier makes no difference. Each thread can still enter its own instance's move method because they have separate locks.

You only need to synchronize when you have some data which is being shared between threads, and at least one thread is modifying that data.

You need to understand how synchronization works. Threads take a 'lock' on the object on which you are synchronizing when they enter the synchronized block. If you have a synchronized method then in that case the object becomes the 'this' instance. Now, no 2 threads can take a lock on the same object at the same time. object locks are mutex based in philosophy so only once thread can hold the mutex at a time. When the thread holding the lock exits the synchronized method or the block, it releases the mutex and thus the object lock becomes available to other threads to request lock on.

This link explains the concepts excellently. It has pictures about disassembled byte code which shows how threads take and leave locks and why 2 threads on 2 different object dont block each other.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM