0

The problem is that I don't see the effect of synchronizing the block. In Theory, I know it's suppose to lock the block until it's done with the thread it would be processing at the time. When I run the following code with or without the synchronized block, nothing changes, well, at least that's what I think. Basically, How do I make these threads display in an orderly manner? Please clear it up for me, thanks.

public class Threads9 extends Thread{
    private String name;

    public Threads9(String paramName){
        name = paramName;
    }

    public void run() {
        print();
    }
    private void print() {
        synchronized(this){
        for(int i = 0;i<10;i++){
            System.out.println(name+ " looping");
        }
      }
    }
}

public class Threads9Main{
    public static void main(String[] args) {

        Threads9 thread1 = new Threads9("Thread1");
        Threads9 thread2 = new Threads9("Thread2");

        thread1.start();
        thread2.start();
    }
}
Sello Nyama
  • 71
  • 1
  • 10
  • 1
    Using `System.out.println(...)` is not a good idea since this method is not thread-safe (e.g. it is not guaranteed that output is written in the same order as `System.out.println(...)` was called). Maybe you want to take a look at [this tutorial](https://docs.oracle.com/javase/tutorial/essential/concurrency/syncmeth.html). – Turing85 May 16 '16 at 08:29
  • 1
    The two threads are synchronizing on different objects. – David Schwartz May 16 '16 at 09:11
  • Re, "... nothing changes." That's an extremely weak way to describe the problem that you are seeing. You got lucky this time, but the best way to get help on this site (i.e., the way to get the best help) is to show us your code, tell us in detail what you thought it would do, tell us how it failed to meet your expectations (including the complete text of any unexpected error messages), and then ask us what went wrong. – Solomon Slow May 16 '16 at 12:57
  • P.S.: Don't think of "synchronized threads." Think about synchronizing _access to shared data_. The entire point of `synchronized` blocks it to prevent threads from seeing (and maybe from operating on) data that is in an invalid state because of the operation of some other thread. – Solomon Slow May 16 '16 at 13:01

3 Answers3

1

You're synchronizing on "this" and it's different between the threads. Try to synchronize on: Threads9.class and it'll work. Also, increase the loop size drastically, or the first will finish before the second starts.

Shimi Bandiel
  • 5,773
  • 3
  • 40
  • 49
  • 1
    As I have recently been informed while you are right that locking on `Thread9.class` will work it is better practise to lock on an explicit monitor as other unrelated objects could be locking on the class object. – Lee May 16 '16 at 08:41
  • Maybe. However, by allowing others to also lock on the object (class) you can decrease deadlock probability (all depends, as usual, on the use-case). – Shimi Bandiel May 17 '16 at 05:58
0

Your objects are not sharing a monitor so you won't have any inter-Thread communication.

Try:

public class Threads9 extends Thread{ private String name;

    private static Object lock = new Object();

    public Threads9(String paramName){
        name = paramName;
    }

    public void run() {
        print();
    }

    private void print() {
        synchronized(lock){
            for(int i = 0;i<10;i++){
                System.out.println(name+ " looping");
            }
        }
    }
}
Lee
  • 738
  • 3
  • 13
  • But the problem now is that it only shows me the last thread a lot of times. How can I make it show the appropriate threads and one after another? – Sello Nyama May 16 '16 at 08:43
0

Change your code like this and put synchronized block inside run.

public Threads9(String paramName){
    name = paramName;
}

public void run() {
    synchronized(this){
    print();
    }
}

private void print() {

    for(int i = 0;i<10;i++){
        System.out.println(name+ " looping");
    }

}
Prakash Hari Sharma
  • 1,414
  • 2
  • 17
  • 22