Question: What is the difference between Daemon Thread and User Thread ?
Answer:
Daemon Thread:
A daemon thread is a thread which is created by JVM for any background task like garbage collection or any other house keeping task.
When the JVM exits, all the daemon threads get stopped immediately- No finally methods will be called, no stacks un-winding happens, it simply exits.
To make an user thread to daemon you have to do this: t1.setDaemon(true). Where t1 is an thread object.
You have to do this before you call start() method on it. After that if you try to do you will get exception- IllegelThreadStateException.
Main thread can’t be made a daemon thread. Why?
Because main thread is already started, once a thread is started and running you can’t change it to a daemon thread. Simple.
User Thread:
A normal thread is called as an user thread, which is created out of Thread, Runnable or Callable interfaces.
Main thread is also an example of user thread.
Whenever all the user threads are completely executed, JVM exits.
Question: Why wait(), notify() and notifyAll() are present in Object class ?
Object class has Monitors, which is being used by threads to get hold of to get the lock of an object. Thread class doesn’t have this monitor.
Due to this reason wait(), notify() and notifyAll() is present in Object class. Basically these methods are used for inter thread commnunication.
To understand in a layman language, Object class is a super class to Thread class. Something present in the super class has an commanding position. If there is any deadlock in threads, it would be easy if those methods are not present in threads, rather it should be present in some other class and better if in some super class, so that it could be called easily.
Question: Difference between sleep() and wait() ?
Answer:
sleep():
- It is a static method in Thread class, thats why we call Thread.sleep(1000).
- The reason of making it a static- it is called on the current executing thread and not on any other executing or non-executing thread instance.
- you can specify time in milliseconds to it.
- when the time is over or somebody calls interrup() it returns back to runnable state.
- it holds the lock when it goes to sleep state.
- no need to call inside the synchronized block.
- this method can be used for time synchronization.
try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); }
t1.sleep(1000); //this will not make the t1 thread to go on sleep, rather the current thread goes to sleep.
wait():
- is called on a object (and not specifically on a thread object), since wait() is present in Object class.
- we don’t specify time to this method.
- it comes to runnable state only when we call notify() or notifyAll().
- it doesn’t hold the object lock while in waiting state.
- it is advisable to write this inside a synchronized block since we have to take the object lock.
- this method can be used for multi-thread synchronization.
- its not a static method.
try{ wait(); }catch (InterruptedException e){ e.printStackTrace(); }
Question: What is thread pool. Give an example ?
Answer:
Thread pool is a reservoir of threads, where multiple threads were created and assigned and re-assigned some task by the service provider.
Java provides Executor framework which consists of Executor interface, ExecutorService interface (which is a sub interface of Executor interface) and ThreadPoolExecutor class.
class MyRunnable implements Runnable{ public void run() { System.out.println(Thread.currentThread().getName()+" Start ---"); try { Thread.sleep(5000); //dummy work. } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName()+" End ***"); } } public class Manager { public static void main(String[] args) { //Creating a thread pool of size 3. ExecutorService executorService = Executors.newFixedThreadPool(3); //Below loop is a kind of timer loop, more the number, more time it will run and assign work to threads: for (int i = 0; i <= 5; i++) { Runnable r = new MyRunnable(); executorService.execute(r); } executorService.shutdown(); while (!executorService.isTerminated()) { //This block will make sure control does not go the last line. } System.out.println("Finished all threads"); } }
Question: Difference between Runnable and Callable ?
- Runnable has run() and Callable has call().
- run() returns void and call() return a value
- Runnable was introduced in java 1.0 and Callable was introduced in java 5.0
- run() can not throws a checked exception, call() can throw a checked exception.
public interface Runnable{ public abstract void run(); }
public interface Callable<V>{ V call() throws exception ; }
Question: What is the use of FutureTask?
FutureTask can be used where we want to store our returned values from a call().
Below is the example code:
class MyCallable implements Callable{ public String call() { System.out.println(Thread.currentThread().getName()+" Start ---"); try { Thread.sleep(5000); //dummy work. } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName()+" End ***"); return "10"; } } public class Manager{ public static void main(String[] args) throws ExecutionException, InterruptedException{ ExecutorService executorService = Executors.newFixedThreadPool(3); FutureTask[] ft=new FutureTask[5]; for (int i = 0; i < 5; i++) { MyCallable r = new MyCallable(); ft[i]=new FutureTask(r); executorService.execute(ft[i]); } executorService.shutdown(); while (!executorService.isTerminated()) { } System.out.println("Finished all threads " ); System.out.println("Printing the returned results from all threads:"); for(int i=0;i<ft.length;i++) { System.out.println(ft[i].get()); } } }
Question: What are atomic operation. What are the atomic classes?
Answer:
Generally in java, whenever we do any operation on an integer like i++, by the time the operation is getting done some other threads might come and do another ++ operation on it. This would raise further complications. It means that the i++ operation is not an atomic one, it can further be broken down to some tiny processes. Although this problem can be solved by Synchronization, but synchronization has its own overheads.So, java came up with atomic classes in concurrent package:
For example, the below code is a normal run() implementation in MyRunnable class:
private int count; public void run() { for (int i = 1; i < 5; i++) { processSomething(i); count++; } }
And the below codes would be with an atomic class:
import java.util.concurrent.atomic.AtomicInteger; //some codes private AtomicInteger count = new AtomicInteger(); public void run() { for (int i = 1; i < 5; i++) { processSomething(i); count.incrementAndGet(); } }
Question: What is Reentrant Lock ?
Answer:
As the name suggest, using Reentrant lock a thread can hold the lock multiple times, i.e., the thread can enter the critical area multiple times, unlikely in synchronized block/method where a thread can hold lock only once. In Reentrank lock there is a mechanism of waiting queue, unlikely in synchronized keyword and due to which some threads gets to starvation.
Reentrant lock is an un-structured, unlike synchronized keyword which is a structured construct.
Its in java.util.concurrent package and added in java 1.5.
Suppose for the below code:
public void a(){ synchronized(this){ //code to be synchronized } }
The above code can be re-written in Reentrant lock:
Lock lock=new ReentrantLock(); public void a(){ lock.lock(); //code to be synchronized. lock.unlock(); }
Even you can hold your lock across methods which is not possible using synchronized constructs:
Lock lock=new ReentrantLock(); public void a(){ lock.lock(); //code to be synchronized. } public void b(){ //some other code. lock.unlock(); }
Better keep the code to be synchronized in a try-catch block and the unlock in a finally block.
Or you can use the tryLock() instead of lock() like below:
lock.tryLock(10, TimeUnit.SECONDS); //(Time to wait for the lock, Time unit) //code to be synchronized lock.unlock();
In the above tryLock() the 1st parameter is: time to wait for the lock, and the 2nd parameter is: time unit
Question: How to make your code thread safe ?
You can synchronize your code and for that you can use either of the below way:
class A { public synchronized void methodA() { //some code } }
class A { public void methodA(){ synchronized(this){ // some code } } }
There are 2 types of locks to be acquired by a thread- object level lock & class level lock.
A thread has to acquire an object level lock whenever it has to enter an non-static synchronized code.
A thread has to acquire an class level lock whenever it has to enter an static synchronized code.
Question: For the below code, if a thread is already accessing methodA() can any other thread access the methodB() ?
class A { public synchronized void methodA() { //some code } public synchronized void methodB() { //some code } }
Lets Analyse:
Does this class has any Static methods ? No, so there is no chance of getting the Class Level Lock.
Now, lets assume Class A has 2 objects- a1 and a2. Object a1 has 3 threads- t1,t2,t3 and a2 has 3 threads to compete- t4,t5,t6.
Now, t1 got hold of methodA()- so what it would have done ? It would have taken hold of the object level lock.
Once t1 got that object there is no more locks available for threads of a1 object, so no chance of other threads of a1 object to either enter methodA() nor methodB(). But, threads from a2 can compete and enter either methodA() or methodB(), because every object has their own object lock, unlikely for class lock, which is single and global in nature.
Question: For the below code, whether any other thread can access the other methods if a thread has entered methodA() ?
class A { public synchronized void methodA() { methodB(); } public synchronized void methodB() { methodC(); } public synchronized void methodC() { //some code } }
Lets Analyse:
In the above code if t1 of a1 has entered to methodA(), other threads t2 and t3 of a1 has to wait, they can’t enter. Here, methodA() is calling methodB(), methodA() already has the lock, it will not release the lock and it will enter methodB(), similarly it will further call methodC(). Till everything is finished no other threads of a1 can enter. Simple.