Reputation: 21
import java.util.logging.Level;
import java.util.logging.Logger;
public class test {
private static void m1(final String a) {
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
try {
Thread.sleep(1000);
System.out.print(a);
} catch (InterruptedException ex) {
Logger.getLogger(test.class.getName()).log(Level.SEVERE,
null, ex);
}
}
});
t1.start();
}
private static void m2(final String a) {
Thread t2 = new Thread(new Runnable() {
@Override
public void run() {
try {
Thread.sleep(1000);
System.out.print(" " + a);
} catch (InterruptedException ex) {
Logger.getLogger(test.class.getName()).log(Level.SEVERE,
null, ex);
}
}
});
t2.start();
}
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
m1("Mihi");
m2("Cherub");
System.out.println("");
}
}
}
I wanna get output as MihiCherub MihiCherub Likewise 10 times
but now my output is "MihiMihi Cherub CherubMihi CherubMihiMih". I wanna sync my two methods and want to get result as mihicherub. Please Help..
Upvotes: 2
Views: 116
Reputation: 19185
With the use of CountDownLatch
you can achieve this but it not an efficient approach. I have modified your code as below.
import java.util.concurrent.CountDownLatch;
import java.util.logging.Level;
import java.util.logging.Logger;
public class test {
private static void m1(final String a, final CountDownLatch sharedCountDownLatch,
final CountDownLatch masterCountDownLatch,
final CountDownLatch doneCountDownLatch) {
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
try {
sharedCountDownLatch.countDown();
sharedCountDownLatch.await();
System.out.print(a);
masterCountDownLatch.countDown();
} catch (InterruptedException ex) {
Logger.getLogger(test.class.getName()).log(Level.SEVERE,
null, ex);
} finally {
doneCountDownLatch.countDown();
}
}
});
t1.start();
}
private static void m2(final String a, final CountDownLatch sharedCountDownLatch,
final CountDownLatch masterCountDownLatch,
final CountDownLatch doneCountDownLatch) {
Thread t2 = new Thread(new Runnable() {
@Override
public void run() {
try {
sharedCountDownLatch.countDown();
sharedCountDownLatch.await();
masterCountDownLatch.await();
System.out.print(" " + a + " ");
} catch (InterruptedException ex) {
Logger.getLogger(test.class.getName()).log(Level.SEVERE,
null, ex);
} finally {
doneCountDownLatch.countDown();
}
}
});
t2.start();
}
public static void main(String[] args) throws InterruptedException {
for (int i = 0; i < 10; i++) {
CountDownLatch doneCountDownLatch = new CountDownLatch(2);//CountDownLatch which will be to ensure that both threads executed.
CountDownLatch sharedCountDownLatch = new CountDownLatch(2);//CountDownLatch that will be shared between both threads so that it will ensure that both threads are at the same execution point
CountDownLatch masterCountDownLatch = new CountDownLatch(1);//CountDownLatch which will be used when master thread completes it work
m1("Mihi", sharedCountDownLatch, masterCountDownLatch,
doneCountDownLatch);
m2("Cherub", sharedCountDownLatch, masterCountDownLatch,
doneCountDownLatch);
System.out.println("");
doneCountDownLatch.await();
}
}
}
Which outputs as :
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Mihi Cherub
Upvotes: 0
Reputation: 533870
If you want to synchronize the behaviour, the best thing to do is to use one thread.
Thread are designed for relatively independent tasks, the more independent the better.
You can do what you want with synchronize, wait and notify but it will be relatively complicated (and pointless)
In your case, the println("")
will execute before any of the other print(). Is that intented?
Upvotes: 2