Java - print sequence of numbers using two threads with inter thread communication - java

I want to print number in the below format. This should be taken care by two thread t1,t2. Can anyone help to enhance the below code which I have written?
First t1 should print 0-4
Then t2 should print 5-9
Then again t1 should print 10-14
Then t2 should print 15-19
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
class PrintNumber implements Runnable{
String name;
public void run(){
print();
}
synchronized public void print(){
for(int i=0;i< 5;i++){
System.out.println(i+" -- "+Thread.currentThread());
}
}
public static void main(String[] args){
Runnable r = new PrintNumber();
Thread t1 = new Thread(r,"t1");
Thread t2 = new Thread(r,"t2");
t1.start();
t2.start();
}
}

Instead of using the low-level wait() and notify() you can use two Sempaphores.
Each Runnable has a Semaphore it waits for and one it uses to notify the next one.
import java.util.concurrent.Semaphore;
class PrintNumber implements Runnable{
static volatile int nextStartIdx;
private Semaphore waitForSemaphore;
private Semaphore next;
public PrintNumber(Semaphore waitFor, Semaphore next) {
this.waitForSemaphore = waitFor;
this.next = next;
}
public void run(){
while (true) {
print();
}
}
public void print() {
try {
waitForSemaphore.acquire();
int start = nextStartIdx;
for(int i=0;i< 5;i++){
System.out.println(String.format("%d -- %s", i + start, Thread.currentThread().getName()));
}
nextStartIdx += 5;
next.release();
} catch (InterruptedException ie) {
Thread.currentThread().interrupt();
}
}
public static void main(String[] args){
Semaphore a = new Semaphore(1);
Semaphore b = new Semaphore(0);
Thread t1 = new Thread(new PrintNumber(a,b),"t1");
Thread t2 = new Thread(new PrintNumber(b,a),"t2");
t1.start();
t2.start();
}
}

You can use wait and notify to achieve inter thread communication for your sczenario.
class PrintNumber implements Runnable {
String name;
Integer count = 0;
#Override
public void run() {
try {
print();
} catch (final InterruptedException e) {
e.printStackTrace();
}
}
synchronized public void print() throws InterruptedException {
while (count < 15) {
for (int i = 0; i < 5; i++) {
count++;
System.out.println(count + " -- " + Thread.currentThread());
}
notifyAll();
wait();
}
}
public static void main(final String[] args) {
final Runnable r = new PrintNumber();
final Thread t1 = new Thread(r, "t1");
final Thread t2 = new Thread(r, "t2");
t1.start();
t2.start();
}
}
For more information see:
A simple scenario using wait() and notify() in java

Related

How to print number 1 to 31 with three threads in JAVA?

I am trying to print number 1 to 31 In order with Three Threads.
When the number became 31, I want to output "(current Thread) defeated."
Also the number can be output up to 3.
So I want to output like
Thread One print: 1 2
Thread Two print: 3 4 5
Thread Three print: 6 7
Thread One print: 8
......
Thread Three print: 31
Thread Three defeat
and program ends.
public class MyRunnable implements Runnable {
Stack sta = new Stack();
public void run() {
while(sta.getStack()<=31){
int stack = 1;
stack++;
sta.setStack(stack);
System.out.println(Thread.currentThread().getName() + "print: "+ stack);
}
}
}
////////////
public class Stack {
private int stack = 1;
public synchronized void setStack (int stack) {
for(int cnt = 1; cnt<=31; cnt ++) {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
}
System.out.println(Thread.currentThread().getName() + "defeated.");
}
}
public int getStack() {
return this.stack;
}
}
////////////////////
public class ThreadTest {
public static void main(String[] args) {
Runnable threadRun = new MyRunnable();
Thread myThread1 = new Thread(threadRun);
Thread myThread2 = new Thread(threadRun);
Thread myThread3 = new Thread(threadRun);
myThread1.setName("Thread One");
myThread2.setName("Thread Two");
myThread3.setName("Thread Three");
myThread1.start();
myThread2.start();
myThread3.start();
}
}
I made 3 classes.
But it prints only "Thread One output defeat"
I don't know what is problem.
It won't print Thread in order.
I'm not good at using this platform so sorry for looking weird.
I tried a bit and came up with this:
public class MyRunnable implements Runnable {
Stack sta = new Stack();
#Override
public void run() {
while (sta.getStack() <= 31) {
int stack = sta.getStack() + 1;
sta.setStack(stack);
if (stack <= 31) {
System.out.println(Thread.currentThread().getName() + " print: " + stack);
}
}
}
}
public class Stack {
private int stack = 0;
public synchronized void setStack(int stack) {
this.stack = stack;
try {
Thread.sleep(100);
} catch (InterruptedException e) {
}
if (stack > 31) {
System.out.println(Thread.currentThread().getName() + " defeated.");
}
}
public synchronized int getStack() {
return this.stack;
}
}
public class ThreadTest {
public static void main(String[] args) {
Runnable threadRun = new MyRunnable();
Thread myThread1 = new Thread(threadRun);
Thread myThread2 = new Thread(threadRun);
Thread myThread3 = new Thread(threadRun);
myThread1.setName("Thread One");
myThread2.setName("Thread Two");
myThread3.setName("Thread Three");
myThread1.start();
myThread2.start();
myThread3.start();
}
}

Java multithreading : Execute 2 threads one after other to print from 1 to 10 in java

Two threads needs to print in this order-
Thread1:0
Thread2:::0
Thread1:1
Thread2:::1
Thread1:2
Thread2:::2
Thread1:3
Thread2:::3
.
.
.
Thread1:10
Thread2:::10
My current is as below:
package sample;
public class ThreadExecutionOrder {
public static void main(String[] args) throws InterruptedException {
ThreadExecutionOrder th=new ThreadExecutionOrder();
Thread1 t1= new Thread1(th);
Thread t2 = new Thread2(th);
t1.start();
t2.start();
}
}
class Thread1 extends Thread{
ThreadExecutionOrder th;
Thread1(ThreadExecutionOrder th){
this.th=th;
}
#Override
public void run() {
for (int i = 0; i < 10; i++) {
System.out.println("Thread1:"+i);
synchronized(th){
try {
th.wait();
th.notify();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
class Thread2 extends Thread{
ThreadExecutionOrder th;
Thread2(ThreadExecutionOrder th){
this.th=th;
}
#Override
public void run() {
for (int i = 0; i < 10; i++) {
System.out.println("Thread2:::"+i);
synchronized(th){
th.notify();
try {
th.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
This questions was asked in an interview. Please let me know how to solve this with example code. Thanks.
I don’t think that this is a useful task, but it can be implemented like
ExecutorService es = Executors.newFixedThreadPool(2);
Phaser phaser = new Phaser(2);
for(int i = 0; i<2; i++) {
int thread = i;
es.execute(() -> {
String name = "Thread "+(thread+1)+": ";
for(int turn=0; turn<22; turn++) {
phaser.arriveAndAwaitAdvance();
if((turn&1)==thread)
System.out.println(name+turn/2);
}
});
}
es.shutdown();
The lambda expression is only a syntactical thing, not required for the program logic. It would be easy to convert it to Java versions before Java 8. Also, letting the second thread print three colons instead of one (if that really is a requirement), wouldn’t be so hard…
Use a Semaphore for each thread, granting it permission to print the next line of output, like this:
public class CounterThread extends Thread {
private final Semaphore mySemaphore;
private final Semaphore nextSemaphore;
public CounterThread(String name, Semaphore mySemaphore, Semaphore nextSemaphore) {
super(name);
this.mySemaphore = mySemaphore;
this.nextSemaphore = nextSemaphore;
}
#Override
public void run() {
try {
for (int i = 0; i <= 10; i++) {
this.mySemaphore.acquire();
System.out.println(getName() + ":" + i);
this.nextSemaphore.release();
}
} catch (InterruptedException e) {
e.printStackTrace(System.out);
}
}
}
With object monitors, the notify() call only signals threads that are already waiting. If no thread is currently waiting, the signal is "lost".
With semaphores, the release() call adds a permit to the semaphore, which can immediate cause an already waiting thread to begin executing, or it is remembered so some future thread can continue executing when it calls acquire(), without ever entering a wait state.
Test (2 threads)
Semaphore s1 = new Semaphore(0);
Semaphore s2 = new Semaphore(0);
new CounterThread("Thread1", s1, s2).start();
new CounterThread("Thread2", s2, s1).start();
s1.release(); // Start the counting
Output
Thread1:0
Thread2:0
Thread1:1
Thread2:1
Thread1:2
Thread2:2
Thread1:3
Thread2:3
Thread1:4
Thread2:4
Thread1:5
Thread2:5
Thread1:6
Thread2:6
Thread1:7
Thread2:7
Thread1:8
Thread2:8
Thread1:9
Thread2:9
Thread1:10
Thread2:10
Test (4 threads)
Can be used with more than 2 threads:
Semaphore s1 = new Semaphore(0);
Semaphore s2 = new Semaphore(0);
Semaphore s3 = new Semaphore(0);
Semaphore s4 = new Semaphore(0);
new CounterThread("Thread1", s1, s2).start();
new CounterThread("Thread2", s2, s3).start();
new CounterThread("Thread3", s3, s4).start();
new CounterThread("Thread4", s4, s1).start();
s1.release(); // Start the counting
Output
Thread1:0
Thread2:0
Thread3:0
Thread4:0
Thread1:1
Thread2:1
Thread3:1
Thread4:1
Thread1:2
Thread2:2
Thread3:2
Thread4:2
Thread1:3
Thread2:3
Thread3:3
Thread4:3
Thread1:4
Thread2:4
Thread3:4
Thread4:4
Thread1:5
Thread2:5
Thread3:5
Thread4:5
Thread1:6
Thread2:6
Thread3:6
Thread4:6
Thread1:7
Thread2:7
Thread3:7
Thread4:7
Thread1:8
Thread2:8
Thread3:8
Thread4:8
Thread1:9
Thread2:9
Thread3:9
Thread4:9
Thread1:10
Thread2:10
Thread3:10
Thread4:10

How to get same monitor when calling notifyAll()?

main thread creating two thread t1 and t2 run() method of these thread creating two new thread c1 and c2.I want a scenario such that until c1&c2(of t1) are alive t2 will not start executing.
In my code notify and wait are causing Runtime Exception.Since they are not in synchronised block, how to do this?
public class childTcreat2newthread {
public static void main(String[] args) throws InterruptedException {
Thread mainT=Thread.currentThread();
Target ra=new Target("a");
Thread t1=new Thread(ra);
t1.start();
t1.join();
while(ra.getC1().isAlive()==true||ra.getC2().isAlive()==true){
synchronized (mainT) {
mainT.wait();
}}
new Thread(new Target("b")).start();}}
class Target implements Runnable{
Thread c1=new Thread(new Target1("1"));
Thread c2=new Thread(new Target1("2"));
String msg;
Target(String msg){
this.msg=msg;
}
#Override
public void run() {
for(int j=0;j<100000;j++){
for(int i=0;i<10000;i++){
if(i%10000==0&&j%10000==0){System.out.print(msg);}
}}
t1.start();
t2.start();
}
public Thread getC1(){return c1;}
public Thread getC2(){return c2;}
}
class Target1 implements Runnable {
String msg;
Target1(String msg){
this.msg=msg;
}
#Override
public synchronized void run() {
for(int j=0;j<100000;j++){
for(int i=0;i<100000;i++){
if(i%100000==0&&j%10000==0){System.out.print(msg);}
}
}
try{
notifyAll();
System.out.println("K");}catch(IllegalMonitorStateException e){System.out.println("\nIllegalMonitorStateException!! in "+msg+"\n");}
}
}
wait( ) tells the calling thread to give up the monitor and go to sleep until some others thread enters the same monitor and calls notify( ).Unable to get same monitor when calling notify.How to do this?
As for my understanding both the thread t1 & t2 does not have common object here to which these are accessing so which object we should have to pass in synchronised lock to call wait() and notify()?
as #JB Nizet pointed out you should use join to wait fot thread termination
EDIT
since you cannot use join I suggest you to use a CountDownLatch since
its documentation states:
A synchronization aid that allows one or more threads to wait until a set of operations being performed in other threads completes.
Which is what you asked for.
SECOND EDIT
Here is a modified version of your code that wait for thread termination using a HomeMade CountDownLatch that uses wait and notify.
import java.util.concurrent.CountDownLatch;
public class childTcreat2newthread {
public static void main(String[] args) throws InterruptedException {
MyCountDownLatch doneSignal = new MyCountDownLatch(2);
Target ra = new Target("a",doneSignal);
Thread t1 = new Thread(ra);
t1.start();
doneSignal.await();
System.out.println("after await ");
MyCountDownLatch doneSignal1 = new MyCountDownLatch(2);
new Thread(new Target("b",doneSignal1)).start();
}
}
class Target implements Runnable {
private Thread c1;
private Thread c2;
String msg;
Target(String msg, MyCountDownLatch doneSignal) {
this.msg = msg;
c1 = new Thread(new Target1("1",doneSignal));
c2 = new Thread(new Target1("2",doneSignal));
}
#Override
public void run() {
System.out.println("Start of Target " + msg);
for (int j = 0; j < 100000; j++) {
for (int i = 0; i < 10000; i++) {
if (i % 10000 == 0 && j % 10000 == 0) {
System.out.print(msg);
}
}
}
c1.start();
c2.start();
// try {
// c1.join();
// c2.join();
// } catch (InterruptedException e) {
// // TODO Auto-generated catch block
// e.printStackTrace();
// }
System.out.println("End of Target " + msg);
}
public Thread getC1() {
return c1;
}
public Thread getC2() {
return c2;
}
}
class Target1 implements Runnable {
String msg;
private MyCountDownLatch doneSignal;
Target1(String msg, MyCountDownLatch doneSignal) {
this.msg = msg;
this.doneSignal=doneSignal;
}
#Override
public void run() {
System.out.println("Start of Target1 " + msg);
for (int j = 0; j < 100000; j++) {
for (int i = 0; i < 100000; i++) {
if (i % 100000 == 0 && j % 10000 == 0) {
System.out.print(msg);
}
}
}
try {
System.out.println("K");
doneSignal.countDown();
System.out.println("End of Target1 " + msg);
} catch (IllegalMonitorStateException e) {
System.out.println("\nIllegalMonitorStateException!! in " + msg
+ "\n");
}
}
}
class MyCountDownLatch {
private int waitersNum;
public MyCountDownLatch(int waitersNum) {
this.waitersNum=waitersNum;
}
public synchronized void countDown() {
waitersNum--;
if (waitersNum==0) {
notifyAll();
}
}
public synchronized void await() throws InterruptedException {
wait();
}
}
notify, notifyAll, wait calls should be done in the monitor of the same object. There should be a shared object like Object and you should build your logic around that. For example :
public class ClassA{
Object lockObject=new Object();
//Thread A will call this method
public void methodA(){
synchronized(lockObject){
while(!aCondition)
lockObject.wait();
}
}
//Thread B will call this method
public void methodB(){
synchronized(lockObject){
aCondition=true;
lockObject.notify();
}
}
}

Execute two threads which wait one for the other while main thread continues

How can I start two threads where thread1 executes first, thread2 starts when thread1 ends while the main method thread can continue its work without locking on the other two?
I have tried join() however it needs to be called from the thread which has to wait for the other, there's no way to do something like thread2.join(thread1);
If I call for a join inside main() I therefore effectively stop execution of the main thread and not only of thread2.
I therefore tried with ExecutorService but again same problem.
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
public class Test
{
public static void main(String args[]) throws InterruptedException
{
System.out.println(Thread.currentThread().getName() + " is Started");
class TestThread extends Thread
{
String name;
public TestThread(String name)
{
this.name = name;
}
#Override
public void run()
{
try
{
System.out.println(this + " is Started");
Thread.sleep(2000);
System.out.println(this + " is Completed");
}
catch (InterruptedException ex) { ex.printStackTrace(); }
}
#Override
public String toString() { return "Thread " + name; }
}
ExecutorService executor = Executors.newCachedThreadPool();
executor.execute(new TestThread("1"));
boolean finished = executor.awaitTermination(1, TimeUnit.HOURS);
if(finished)
{
//I should execute thread 2 only after thread 1 has finished
executor.execute(new TestThread("2"));
}
//I should arrive here while process 1 and 2 go on with their execution
System.out.println("Hello");
}
}
#EDIT: Why I need this:
I need this because Thread1 copies elements from a database table into another database, thread2 has to copy a linking table which references the table copied from thread1.
Consequently thread2 has to start populating its linking table only when thread1 has finished otherwise an integrity error is given by the database.
Now imagine I have several threads with different priorities due to complex linking tables and you have an idea.
The second Thread can be custom like this (takes as argument the previous thread):
public static void main(String[] a) {
Thread first = new Thread(new Runnable() {
#Override
public void run() {
}
});
Thread second = new MyThread(first);
first.start();
second.start();
//continue executing
}
public static class MyThread extends Thread {
private Thread predecessor;
public MyThread(Thread predecessor) {
this.predecessor = predecessor;
}
public void run() {
if (predecessor != null && predecessor.isAlive()) {
try {
predecessor.join();
} catch (InterruptedException e) {}
}
//do your stuff
}
}
You can use a CountDownLatch:
create it in the main thread, pass it on to both threads and call countdown on it in thread one when it exits and await it being counted down at the start of thread 2.
I am pretty sure you got something wrong because this must work and it does work:
new Thread() {
#Override
public void run() {
TestThread t1= new TestThread("1");
TestThread t2= new TestThread("2");
try {
t1.start();
t1.join();
t2.start();
t2.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}.start();
The ouput is:
main is Started
Hello
Thread 1 is Started
Thread 1 is Completed
Thread 2 is Started
Thread 2 is Completed
Another option would be to extend the TestThread for the "Thread 1" to execute the work of "Thread 2" after it has been done with its own work. Something similar to this:
final TestThread t2= new TestThread("2");
TestThread t1= new TestThread("1") {
#Override
public void run() {
super.run(); //finish t1 work
t2.start(); // start t2 work
}
};
t1.start();
Why not just have thread1 be the one to start thread2?
// in main
new Thread(new Runnable() {
#Override public void run() {
// do thread1 work
new Thread(new Runnable() {
#Override public void run() { /* do thread2 work */ }
}).start();
}
}).start();
However, it's not at all clear why you would want to do this as opposed to just having thread1 do 100% of the background work.
You can use SingleThreadExecutor to run one task after another Java doc
So it will put your task one after another and they will execute in sequence without blocking main thread
Try this, This will work as expected. Two threads printing odd and even one after another and main exiting as soon as possible.
public class YoThreD {
static boolean isThread1 = false;
public static synchronized boolean isThread1() {
return isThread1 = !isThread1;
}
public static void main(String args[]) {
Runnable runnableObject = new Runnable() {
#Override
public void run() {
synchronized (this) {
for (int i = 1; i <= 100; i++) {
try {
if (Thread.currentThread().getName().equals("thread1")) {
if (isThread1()){
System.out.println(Thread.currentThread().getName() + " : " + i);
}else{
this.notify();
this.wait();
}
} else {
if (!isThread1()){
System.out.println(Thread.currentThread().getName() + " : " + i);
this.notify();
this.wait();
}
else{
}
}
} catch (Exception e) {
}
}
}
}
};
Thread thread1 = new Thread(runnableObject);
thread1.setName("thread1");
thread1.start();
Thread thread2 = new Thread(runnableObject);
thread2.setName("thread2");
thread2.start();
System.out.println(Thread.currentThread().getName() + "Main thread finished");
}
}
Silly question, but if thread 2 is supposed to execute when thread 1 is done... why not just start it from thread 1?
Or maybe just have thread 1 trigger an event and the main thread can just launch the new one in response to that.
I found this example, should work for you.
You can run two thread one after other by using several ways:
by using join() method. ex:
Thread t1=new Thread(new Runnable() {
#Override
public void run() {
for (int i = 0; i < 4; i++) {
System.out.println("A " + i);
}
}
});
Thread t2=new Thread(new Runnable() {
#Override
public void run() {
for (int i = 0; i < 4; i++) {
System.out.println("B " + i);
}
}
});
by using wait() and notify() methods: ex.
`
{
public class NotiffyAllExample {
int flag = 1;
public static void main(String[] args) {
NotiffyAllExample notiffyAllExample = new NotiffyAllExample();
A1 a = new A1(notiffyAllExample);
B1 b = new B1(notiffyAllExample);
C1 c = new C1(notiffyAllExample);
a.start();
b.start();
}
}
class A1 extends Thread {
NotiffyAllExample notiffyAllExample;
public A1(net.citigroup.mexico.pg.test.test.NotiffyAllExample notiffyAllExample) {
this.notiffyAllExample = notiffyAllExample;
}
#Override
public void run() {
try {
synchronized (notiffyAllExample) {
for (int i = 0; i < 4; i++) {
while (notiffyAllExample.flag != 1) {
notiffyAllExample.wait();
}
System.out.print("A ");
}
notiffyAllExample.flag = 2;
notiffyAllExample.notifyAll();
}
} catch (Exception e) {
System.out.println("Exception 1 :" + e.getMessage());
}
}
}
class B1 extends Thread {
NotiffyAllExample notiffyAllExample;
public B1(NotiffyAllExample notiffyAllExample) {
this.notiffyAllExample = notiffyAllExample;
}
#Override
public void run() {
try {
synchronized (notiffyAllExample) {
for (int i = 0; i < 4; i++) {
while (notiffyAllExample.flag != 2) {
notiffyAllExample.wait();
}
System.out.print("B ");
}
notiffyAllExample.flag = 1;
notiffyAllExample.notifyAll();
}
} catch (Exception e) {
System.out.println("Exception 2 :" + e.getMessage());
}
}
}
}
`

Interview: How to ensure that a thread runs after another?

There are thread T1, T2 and T3, how can we ensure that thread T2 run after T1 and thread T3 run after T2?
This question was asked in my interview. I didn't answer. Please explain in detail.
This would be the simplest, dumbest approach:
final Thread t1 = new Thread(new T1()); // assume T1 is a Runnable
t1.start();
t1.join();
final Thread t2 = new Thread(new T2());
t2.start();
t2.join();
final Thread t3 = new Thread(new T3());
t3.start();
t3.join();
The obvious, and simplest, way has already been posted by #Assylias - have T1 run method create/start T2 and T2 run method create/start T3.
It is, IMHO, verging on pointless, but it could be done.
Solutions using Join() do not answer the question - they ensure that the termination of the threads is ordered, not the running of them. If the interviewr does not get that, you need to find another job anyway.
In an interview, my answer would be 'For * sake why? Threads are ususally used to avoid exactly what you are asking!'.
One way to do it would be something like the following. It's complex though. You might want to use the java.util.concurrent.CyclicBarrier class for this.
Each thread when it finishes sets the boolean value and notifies the next thread to continue. Even though it is an AtomicBoolean class, we need the synchronized so we can wait() and notify() on it.
It would be cleaner to pass in the lock objects or maybe have a begin() method on T2 and T3 so we can hide the locks inside of those objects.
final Object lock2 = new Object();
final Object lock3 = new Object();
boolean ready2;
boolean ready3;
...
public T1 implements Runnable {
public void run() {
...
synchronized (lock2) {
// notify the T2 class that it should start
ready2 = true;
lock2.notify();
}
}
}
...
public T2 implements Runnable {
public void run() {
// the while loop takes care of errant signals
synchronized (lock2) {
while (!ready2) {
lock2.wait();
}
}
...
// notify the T3 class that it should start
synchronized (lock3) {
ready3 = true;
lock3.notify();
}
}
}
...
public T3 implements Runnable {
public void run() {
// the while loop takes care of errant signals
synchronized (lock3) {
while (!ready3) {
lock3.wait();
}
}
...
}
}
There are thread T1, T2 and T3, how can we ensure that thread T2 run
after T1 and thread T3 run after T2?
OR
There are three threads T1, T2 and T3? How do you ensure sequence T1, T2, T3 in Java?
The question basically is T3 should finish first , T2 second and T1 last.
We can use use join() method of thread class.
To ensure three threads execute you need to start the last one first e.g. T3 and then call join methods in reverse order e.g. T3 calls T2.join,
and T2 calls T1.join. In this way, T1 will finish first and T3 will finish last.
public class Test1 {
public static void main(String[] args) {
final Thread t1 = new Thread(new Runnable() {
public void run() {
System.out.println("start 1");
System.out.println("end 1");
}//run
});
final Thread t2 = new Thread(new Runnable() {
public void run() {
System.out.println(" start 2 ");
try {
t1.join(2000);
} catch (Exception e) {
e.getStackTrace();
}
System.out.println(" end 2");
}
}) ;
final Thread t3 = new Thread( new Runnable() {
public void run() {
System.out.println(" start 3 ");
try {
t2.join(4000);
}catch(Exception e) {
e.getStackTrace();
}
System.out.println(" end 3 ");
}
});
// we are reversing the order of the start() method
t3.start();
t2.start();
t1.start();
}
}
From the output, You can see that threads have started in different order as you don't know which thread will get CPU. Its the decision of the Thread Scheduler, so we cannot do anything. But, you can see that threads are finished in correct order i.e. T1 then T2 and then T3.
There is another way of doing it. The pseudo code is :
t1.start();
t1.join(); // signals t2 to wait
if( !t1.isAlive()) {
t2.start();// if t1 is finished then t2 will start
}
t2.join();//signals t3 to wait
if (!t2.isAlive()) {
t3.start();
}
Let's take a full program:
public class Tic implements Runnable{
public void run() {
try {
for (int i = 0; i < 2; i++) {
System.out.println("tic");
}
} catch (Exception e) {
// TODO: handle exception
e.getStackTrace();
}
}
}
public class Tac implements Runnable{
public void run() {
try {
for (int i = 0; i < 2; i++) {
System.out.println("tac");
}
} catch (Exception e) {
// TODO: handle exception
e.getStackTrace();
}
}
}
public class Toe implements Runnable{
public void run() {
try {
for (int i = 0; i < 2; i++) {
System.out.println("toe");
}
} catch (Exception e) {
// TODO: handle exception
e.getStackTrace();
}
}
}
public class RunThreads1 {
public static void main(String[] args) {
try {
Tic tic = new Tic();
Tac tac = new Tac();
Toe toe = new Toe();
Thread t1 = new Thread(tic);
Thread t2 = new Thread(tac);
Thread t3 = new Thread(toe);
t1.start();
t1.join(); // signals t2 to wait
if( !t1.isAlive()) {
t2.start();// if t1 is finished then t2 will start
}
t2.join();//signals t3 to wait
if (!t2.isAlive()) {
t3.start();
}
}catch(InterruptedException e) {
e.printStackTrace();
}
}
}
The output is :
tic
tic
tac
tac
toe
toe
At the start of each thread (except t1), make it call join() on it's predecessor. Using executors (instead of threads directly) is another option. One could also look at using semaphores - T1 should release the permit upon completion, T2 should try to acquire two permits, and release them when done, T3 should try to acquire three permits & so on. Using join or executors would be the preferred route.
Threads are also runnables. You can simply run them sequentially:
t1.run();
t2.run();
t3.run();
This has obviously little interest.
Assuming they want the threads to run in parallel, one solution would be to have each thread start the next one, since the JMM guarantees that:
A call to start() on a thread happens-before any actions in the started thread.
Guess what interviewer asking was three threads do the work in sequence.For example if one thread prints 1,4,5...second 2,5,8 and thirds 3,6,9 etc..ur output should be 1,2,3,4,5.....
Ist thread prints 1 and gives chance to 2nd thread to print 2..etc.,
I tried it using cyclebarriers.As soon as 'one' prints 1it gives chance to two as it calls cb.wait,when two runs it will in turn call three in similar fashion and it will continue.Let me know if thr are any bugs in the code
import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;
class one implements Runnable{
CyclicBarrier cb;
one(CyclicBarrier cb){this.cb=cb;}
public void run(){
int i=1;
while(true)
{
System.out.println(i);
try {
Thread.sleep(1000);
cb.await();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (BrokenBarrierException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
i=i+3;
}
}
}
class two implements Runnable{
CyclicBarrier cb;
int i=2;
two(CyclicBarrier cb){this.cb=cb;}
public void run(){
System.out.println(i);
try {
cb.await();
i=i+3;
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (BrokenBarrierException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
public class oneTwoThree {
public static void main(String args[]){
Runnable threePrinter = new Runnable() {
int i=3;
public void run() {
System.out.println(i);
i=i+3;
}
};
CyclicBarrier bar2 =new CyclicBarrier(1,threePrinter);//, barrier1Action);
two twoPrinter =new two(bar2);
CyclicBarrier bar1 =new CyclicBarrier(1,twoPrinter);
Thread onePrinter=new Thread(new one(bar1));
onePrinter.start();
}
}
I tried in a much simpler way.. using a waits and notifies.(as opposed to cyclic barrier approach in my prev post).
It uses a 'State' class... which gets three states:1,2,3.(default 3).
When it is at 3, it triggers t1, at 1 will trigger t2, at 2 will trigger t3 and so on.
Classes:
State// int i=3
T1// prints 1,4,7...
T2// Prints 2,5,8
T3//Prints 3,6,9 etc.,
Please let me know your views or if any issues in the code. Thanks.
Here is the code.:
public class State {
private int state ;
public State() {
this.state =3;
}
public synchronized int getState() {
return state;
}
public synchronized void setState(int state) {
this.state = state;
}
}
public class T1 implements Runnable {
State s;
public T1(State s) {
this.s =s;
}
#Override
public void run() {
int i =1;
while(i<50)
{
//System.out.println("s in t1 "+ s.getState());
while(s.getState() != 3)
{
synchronized(s)
{
try {
s.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
synchronized(s)
{
//if(s.getState() ==3)
if(s.getState()==3)
System.out.println("t1 "+i);
s.setState(1);
i = i +3 ;
s.notifyAll();
}
}
}
}
public class T2 implements Runnable {
State s;
public T2(State s) {
this.s =s;
}
#Override
public synchronized void run() {
int i =2;
while(i<50)
{
while(s.getState() != 1)
{
synchronized(s)
{
try {
s.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
synchronized(s)
{
//if(s.getState() ==3)
if(s.getState()==1)
System.out.println("t2 "+i);
s.setState(2);
i = i +3 ;
s.notifyAll();
}
}
}
}
public class T3 implements Runnable {
State s;
public T3(State s) {
this.s =s;
}
#Override
public synchronized void run() {
int i =3;
while(i<50)
{
while(s.getState() != 2)
{
synchronized(s)
{
try {
s.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
synchronized(s)
{
if(s.getState()==2)
System.out.println("t3 "+i);
i = i +3 ;
s.setState(3);
s.notifyAll();
}
}
}}
public class T1t2t3 {
public static void main(String[] args) {
State s = new State();
Thread t1 = new Thread(new T1(s));
Thread t2 = new Thread(new T2(s));
Thread t3 = new Thread(new T3(s));
t1.start();
t2.start();
t3.start();
}
}
how can we ensure that thread T2 run after T1 and thread T3 run after T2?
NOTE: Assuming that it is not about scheduling the threads in the required order
We could use the Condition Interface.
We'll need two conditions bound to a single Lock: condition1 to coordinate T1 and T2, condition2 to coordinate T2 and T3.Pass condition1 to T1 and T2, condition2 to T2 and T3.
So, we would have T2 await on condition1 in it's run method, which will be signalled by T1 (from T1's run method, after T1 starts/finishes its task). Similarly have T3 await on condition2 in it's run method, which will be signalled by T2 (from T2's run method, after it starts/finishes it's task).
Create a priority queue with each tread in the other they are created.
You can then apply Thread.join after it completes, remove that thread from the priority queue, and then execute the first element of the queue again.
Pseudocode:
pthread [3] my_threads
my_queue
for t in pthreads:
my_queue.queue(t)
while !my_queue.empty()
pop the head of the queue
wait until it complets
thread.join()
implementation is left as exercise, so next time you get it right!
Use the thread isAlive method before starting the thread T2 and T3.
Thread t1 = new Thread(new T1());
Thread t2 = new Thread(new T2());
Thread t3 = new Thread(new T3());
t1.start();
if(t1.isAlive()){
t2.start();
}
if(t2.isAlive()){
t3.start();
}
Try the below code while using that you can run n number of thread in that manner.
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class CyclicExecutionOfThreads {
public static void main(String args[]) {
int totalNumOfThreads = 10;
PrintJob printJob = new PrintJob(totalNumOfThreads);
/*
MyRunnable runnable = new MyRunnable(printJob, 1);
Thread t1 = new Thread(runnable);
MyRunnable runnable2 = new MyRunnable(printJob, 2);
Thread t2 = new Thread(runnable2);
MyRunnable runnable3 = new MyRunnable(printJob, 3);
Thread t3 = new Thread(runnable3);
t1.start();
t2.start();
t3.start();
*/
//OR
ExecutorService executorService = Executors
.newFixedThreadPool(totalNumOfThreads);
Set<Runnable> runnables = new HashSet<Runnable>();
for (int i = 1; i <= totalNumOfThreads; i++) {
MyRunnable command = new MyRunnable(printJob, i);
runnables.add(command);
executorService.execute(command);
}
executorService.shutdown();
}
}
class MyRunnable implements Runnable {
PrintJob printJob;
int threadNum;
public MyRunnable(PrintJob job, int threadNum) {
this.printJob = job;
this.threadNum = threadNum;
}
#Override
public void run() {
while (true) {
synchronized (printJob) {
if (threadNum == printJob.counter) {
printJob.printStuff();
if (printJob.counter != printJob.totalNumOfThreads) {
printJob.counter++;
} else {
System.out.println();
// reset the counter
printJob.resetCounter();
}
printJob.notifyAll();
} else {
try {
printJob.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
}
class PrintJob {
int counter = 1;
int totalNumOfThreads;
PrintJob(int totalNumOfThreads) {
this.totalNumOfThreads = totalNumOfThreads;
}
public void printStuff() {
System.out.println("Thread " + Thread.currentThread().getName()
+ " is printing");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public void resetCounter() {
this.counter = 1;
}
}
The concurrent package has better classes to use the shared object.
One of the way is like this.
public static void main(String[] args) {
final Lock lock = new ReentrantLock();
final Condition condition = lock.newCondition();
ThreadId threadId = new RunInSequence.ThreadId();
threadId.setId(1);
Thread t1 = setThread("thread1",lock, condition, 1, 2, threadId);
Thread t2 = setThread("thread2",lock, condition, 2, 3, threadId);
Thread t3 = setThread("thread3",lock, condition, 3, 1, threadId);
t1.start();
t2.start();
t3.start();
}
private static class ThreadId {
private int id;
public ThreadId() {
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
}
private static Thread setThread(final String name,final Lock lock, final Condition condition, int actualThreadId, int nextThreadId,
ThreadId threadId) {
Thread thread = new Thread() {
#Override
public void run() {
while (true) {
lock.lock();
try {
while (threadId.getId() != actualThreadId) {
try {
condition.await();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(name+"prints: " + actualThreadId);
threadId.setId(nextThreadId);
condition.signalAll();
} finally {
lock.unlock();
}
}
}
};
return thread;
}
package thread;
class SyncPrinter {
public static void main(String[] args) {
SyncPrinterAction printAction1 = new SyncPrinterAction(new int[]{1,5,9,13}, true);
SyncPrinterAction printAction2 = new SyncPrinterAction(new int[]{2,6,10,14}, true);
SyncPrinterAction printAction3 = new SyncPrinterAction(new int[]{3,7,11,15}, true);
SyncPrinterAction printAction4 = new SyncPrinterAction(new int[]{4,8,12,16}, false);
printAction1.setDependentAction(printAction4);
printAction2.setDependentAction(printAction1);
printAction3.setDependentAction(printAction2);
printAction4.setDependentAction(printAction3);
new Thread(printAction1, "T1").start();;
new Thread(printAction2, "T2").start();
new Thread(printAction3, "T3").start();
new Thread(printAction4, "T4").start();
}
}
class SyncPrinterAction implements Runnable {
private volatile boolean dependent;
private SyncPrinterAction dependentAction;
int[] data;
public void setDependentAction(SyncPrinterAction dependentAction){
this.dependentAction = dependentAction;
}
public SyncPrinterAction( int[] data, boolean dependent) {
this.data = data;
this.dependent = dependent;
}
public SyncPrinterAction( int[] data, SyncPrinterAction dependentAction, boolean dependent) {
this.dependentAction = dependentAction;
this.data = data;
this.dependent = dependent;
}
#Override
public void run() {
synchronized (this) {
for (int value : data) {
try {
while(dependentAction.isDependent())
//System.out.println("\t\t"+Thread.currentThread().getName() + " :: Waithing for dependent action to complete");
wait(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
dependentAction.setDependent(true);
System.out.println(Thread.currentThread().getName() + " :: " +value);
dependent = false;
}
}
}
private void setDependent(boolean dependent) {
this.dependent = dependent;
}
private boolean isDependent() {
return dependent;
}
}
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
class Worker implements Runnable {
BlockingQueue<Integer> q = new LinkedBlockingQueue<>();
Worker next = null; // next worker in the chain
public void setNext(Worker t) {
this.next = t;
}
public void accept(int i) {
q.add(i);
}
#Override
public void run() {
while (true) {
int i;
try {
i = q.take(); // this blocks the queue to fill-up
System.out.println(Thread.currentThread().getName() + i);
if (next != null) {
next.accept(i + 1); // Pass the next number to the next worker
}
Thread.sleep(500); // Just sleep to notice the printing.
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
public class PrintNumbersSequentially {
public static void main(String[] as) {
Worker w1 = new Worker();
Worker w2 = new Worker();
Worker w3 = new Worker();
w1.setNext(w2);
w2.setNext(w3);
w3.setNext(w1);
new Thread(w1, "Thread-1: ").start();
new Thread(w2, "Thread-2: ").start();
new Thread(w3, "Thread-3: ").start();
//Till here all the threads have started, but no action takes place as the queue is not filled for any worker. So Just filling up one worker.
w1.accept(100);
}
}
I think this could help you out.
By using join you can ensure running of a thread one after another.
class MyTestThread implements Runnable{
public void run() {
System.out.println("==MyTestThread : START : "+Thread.currentThread().getName());
for(int i = 0; i < 10; i++){
System.out.println(Thread.currentThread().getName() + " :i = "+i);
}
System.out.println("==MyTestThread : END : "+Thread.currentThread().getName());
}
}
public class ThreadJoinTest {
public static void main(String[] args) throws InterruptedException {
Thread thread1 = new Thread(new MyTestThread(), "t1");
Thread thread2 = new Thread(new MyTestThread(), "t2");
thread1.start();
thread1.join();
thread2.start();
thread2.join();
System.out.println("====All threads execution===completed");
}
}
package io.hariom.threading;
//You have three threads T1, T2, and T3, How do you ensure that they finish in order T1, T2, T3 ?
public class ThreadTest1 {
public static void main(String[] args) {
Thread thread1 = new Thread(new MyRunnable(null));
Thread thread2 = new Thread(new MyRunnable(thread1));
Thread thread3 = new Thread(new MyRunnable(thread2));
thread1.start();
thread2.start();
thread3.start();
}
}
class MyRunnable implements Runnable {
Thread t;
MyRunnable(Thread t) {
this.t = t;
}
#Override
public void run() {
if (t != null) {
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName() + " starts");
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + " ends");
}
}
Here is my approach to the problem using CountDownLatch for signalling .
T1 thread after doing its job signal to T2 and T2 to T3.
public class T1T2T3 {
public static void main(String[] args) {
CountDownLatch c1 = new CountDownLatch(1);
CountDownLatch c2 = new CountDownLatch(1);
Thread T1 = new Thread(new Runnable() {
#Override
public void run() {
System.out.println("T1");
c1.countDown();
}
});
Thread T2 = new Thread(new Runnable() {
#Override
public void run() {
//should listen to something from T1
try {
c1.await();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("T2");
c2.countDown();
}
});
Thread T3 = new Thread(new Runnable() {
#Override
public void run() {
try {
c2.await();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("T3");
}
});
T1.start();
T3.start();
T2.start();
}
}

Categories

Resources