Exception Handling Java Interview Questions – Set 06

When do we say an exception is not handled

There is no catch block that names either the class of exception that has been

thrown or a class of exception that is a parent class of the one that has been thrown,

then the exception is considered to be unhandled, in such condition the execution

leaves the method directly as if no try has been executed

What happens if you restart a thread that has already started

Get the following exception:

Exception in thread “main” java.lang.IllegalThreadStateException

at java.lang.Thread.start(Thread.java:595)

at deadlock.DeadlockTest.main(DeadlockTest.java:38)

How can I trace whether the application has a thread leak

If an application has thread leak then with time it will have too many unused threads. Try to find out what type of threads is leaking out.

This can be done using following ways:

  • Give unique and descriptive names to the threads created in application. – Add log entry in all thread at various entry and exit points in threads.
  • Change debugging config levels (debug, info, error etc) and analyze log messages.
  • When you find the class that is leaking out threads check how new threads are instantiated and how they’re closed.
  • Make sure the thread is Guaranteed to close properly by doing following – Handling all Exceptions properly.
  • Make sure the thread is Guaranteed to close properly by doing following
  • Handling all Exceptions properly.
  • releasing all resources (e.g. connections, files etc) before it closes.

How will you fix the above racing issue

This can be fixed a number of ways.

Option 1: Method level synchronization. This is the simplest. As you can see, the increment() method is synchronized, so that the other threads must wait for the thread that already has the lock to execute that method.

import java.util.HashMap;

import java.util.Map;

public class Counter {

//shared variable or resource

private Integer count = Integer.valueOf(0);

private Map<String, Integer> userToNumber = new HashMap<String, Integer>(10);

public synchronized void  increment() {

try {

count = count + 1;

Thread.sleep(50);

Thread thread = Thread.currentThread();

userToNumber.put(thread.getName(), count);

} catch (InterruptedException e) {

e.printStackTrace();

}

}

public Integer getCount(String name) {

return userToNumber.get(name);

}

}

Option 2: Even though the Option 1 is simple, it locks the entire method and can adversely impact performance for long running methods as each thread has to execute the entire method one at a time. So, the Option 1 can be improved by providing block level lock. Lock only those operations that are acting on the shared resource and making it non-atomic.

The code below uses an Object, which has its own lock to ensure that two threads cannot execute both the Operation 1 and 2 at the same time because there is only one lock.

import java.util.HashMap;

import java.util.Map;

public class Counter {

//shared variable or resource

private Integer count = Integer.valueOf(0);

private Map<String, Integer> userToNumber = new HashMap<String, Integer>(10);

private Object mutex = new Object();   // a lock

public void  increment() {

try {

synchronized(mutex) {

count = count + 1;                         //operation 1

Thread.sleep(50);

Thread thread = Thread.currentThread();

userToNumber.put(thread.getName(), count); //operation 2

}

// there could be other operations here that uses the shared resource as read only

} catch (InterruptedException e) {

e.printStackTrace();

}

}

public Integer getCount(String name) {

return userToNumber.get(name);

}

}

Option 3: This is a very trivial, but practical example. The Java 5 introduced locks and locks are better than using just objects for more flexible locking scenarios where Locks can be used in place of synchronized blocks. Locks offer more flexibility than synchronized blocks in that a thread can unlock multiple locks it holds in a different order than the locks were obtained. Here is the code that replaces synchronized with a reentrant lock. Synchronized blocks in Java are reentrant, which means if a Java thread enters a synchronized block of code, and thereby take the lock on the object the block is synchronized on, the thread can enter other Java code blocks synchronized on the same lock object.

For example, here is the demo of reentrant lock.

public class Reentrant{

public synchronized method1(){

method2();    //calls another synchronized method on the same object

}

public synchronized method2(){

//do something

}

}

Here is the Option 3 example using a ReentrantLock.

import java.util.HashMap;

import java.util.Map;

import java.util.concurrent.locks.Lock;

import java.util.concurrent.locks.ReentrantLock;

public class Counter {

// shared variable or resource

private Integer count = Integer.valueOf(0);

private Map<String, Integer> userToNumber = new HashMap<String, Integer>(10);

private Lock mutex = new ReentrantLock(); // a lock

public void increment() {

try {

mutex.lock();

try {

count = count + 1;

Thread.sleep(50);

Thread thread = Thread.currentThread();

userToNumber.put(thread.getName(), count);

} finally {

mutex.unlock(); // finally block is executed even if an

// exception is thrown

}

} catch (InterruptedException e) {

e.printStackTrace();

} finally {

}

}

public Integer getCount(String name) {

return userToNumber.get(name);

}

}

Note that the locks are unlocked in a finally block as it is executed even if an exception is thrown.

The output for the above 3 options will be something like shown below. The order cannot be guaranteed.

But you will get unique numbers assigned for each user.

User-1 value is 1

User-3 value is 2

User-2 value is 3

When InvalidMonitorStateException is thrown? Why

This exception is thrown when you try to call wait()/notify()/notifyAll() any of these methods for an Object from a point in your program where u are NOT having a lock on that object.(i.e. u r not executing any synchronized block/method of that object and still trying to call wait()/notify()/notifyAll()) wait(), notify() and notifyAll() all throw IllegalMonitorStateException. since This exception is a subclass of RuntimeException so we r not bound to catch it (although u may if u want to). and being a RuntimeException this exception is not mentioned in the signature of wait(), notify(), notifyAll() methods.

The following code snippet changes the Counter class to maintain individual counting as in each user counter will be incremented starting from 1.

The following code snippet changes the Counter class to maintain individual counting as in each user counter will be incremented starting from 1. So, the Counter will no longer be the shared resource. The CountingTask class is also modified to loop through each user 2 times as shown below. Is there anything wrong with the code shown below

The Counter class with individual counts

import java.util.HashMap;

import java.util.Map;

 

public class Counter {

 

 private Map<String, Integer> userToNumber = new HashMap<String, Integer>(10);

 

 public void increment() {

  Thread thread = Thread.currentThread();

  if (!userToNumber.containsKey(thread.getName())) {

   userToNumber.put(thread.getName(), Integer.valueOf(1));  //op1

  } else {

   Integer count = userToNumber.get(thread.getName());

   if (count != null) {

    ++count; // op2: increment it

    userToNumber.put(thread.getName(), count); //op3

   }

  }

}

 

 public Integer getCount(String name) {

  return userToNumber.get(name);

 }

}

 

// The counting task that repeats twice for each user

public class CountingTask implements Runnable {

 

 private Counter counter;

 

 public CountingTask(Counter counter) {

  super();

  this.counter = counter;

 }

 

public void run() {

 

  for (int i = 0; i < 2; i++) {

   counter.increment();

   Thread thread = Thread.currentThread();

   System.out.println(thread.getName() + ” value is “

     + counter.getCount(thread.getName()));

  }

 }

}

If each user will be accessed by only one thread, then the above code is thread-safe because each user will be operating on his/her data.

So, only one thread will access the map entry for User-1, and so on.

But, what happens if User-3 has two threads created as shown below.

The Thread 3 and 4 are User 3.

In this scenario, the above code is not thread safe, and it needs to be made atomic with one of the three options discussed above. It can be quite dangerous to assume that one user will be accessed only by one thread.What if in the future, additional threads are added to improve performance per user?

public class CountingManager

{

public static void main(String[] args) throws InterruptedException

{

Counter counter = new Counter(); // create an instance of the Counter

CountingTask task = new CountingTask(counter); // pass the counter to the runnable CountingTask

//Create 10 user threads (non-daemon) from the main thread that share the counter object

Thread thread1 = new Thread(task, “User-1”);

Thread thread2 = new Thread(task, “User-2”);

Thread thread3 = new Thread(task, “User-3”); //user 3

Thread thread4 = new Thread(task, “User-3”); //User 3

//start the threads

thread1.start();

thread2.start();

thread3.start();

thread4.start();

//observe the racing conditions in the output

}

}

If you don’t perform the operations 1 to 3 atomically (i.e. as a unit),

you will get an out put like:

User-1 value is 1

User-1 value is 2

User-3 value is 2

User-3 value is 3

User-3 value is 2

User-3 value is 4

User-2 value is 1

User-2 value is 2

As you can see, the User-3 has the value 2 repeated twice and value 1 is missing. If you apply the one of the options outlined above, you will get an output like:

User-1 value is 1

User-1 value is 2

User-3 value is 1

User-3 value is 2

User-2 value is 1

User-2 value is 2

User-3 value is 3

User-3 value is 4

Hence, the operations 1-3 need to be made atomic if accessed concurrently by multiple threads.Those three operations are

  • storing the initial value
  • incrementing the counter
  • storing the incremented value

Can you write a program with 2 threads, in which one prints odd numbers and the other prints even numbers up to

In Java, you can use wait(  ) and notifyAll(  ) to communicate between threads. The code below demonstrates that:

Note: This a typical example of splitting tasks among threads. A method calls notify/notifyAll( ) as the last thing it does (besides return). Since the printOdd( ) and printEven( ) methods were void, the notifyAll( ) was the last statement. If it were to return some value, the notifyAll( ) would have been placed just before the return statement.

Firstly, create the thread classes and the main method that creates the thread and run it.

package multithreading;

public class NumberGenerator extends Thread {

private NumberUtility numberUtility;

private int maxNumber;

private boolean isEvenNumber;

public NumberGenerator(NumberUtility numberUtility, int maxNumber, boolean isEvenNumber) {

this.numberUtility = numberUtility;

this.maxNumber = maxNumber;

this.isEvenNumber = isEvenNumber;

}

public void run() {

int i = isEvenNumber == true ? 2 : 1;

while (i <= maxNumber) {

if(isEvenNumber == true) {

numberUtility.printEven(i);

}

else {

numberUtility.printOdd(i);

}

i = i + 2;

}

}

public static void main(String[] args) {

NumberUtility numUtility = new NumberUtility(); //<span id=”IL_AD6″ class=”IL_AD”>single</span> instance shared by oddGen and evenGen threads

final int MAX_NUM = 10;

//create 2 threads, one to generate odd numbers and the other to generate even numbers

NumberGenerator oddGen = new NumberGenerator(numUtility, MAX_NUM, false);

NumberGenerator evenGen = new NumberGenerator(numUtility, MAX_NUM, true);

oddGen.start();  //start the thread – invokes the run() method on NumberGenerator

evenGen.start(); //start the thread – invokes the run() method on NumberGenerator

}

}

Next, create the utility class that is used for communicating between the two threads with wait() and notifyAll() methods via synchronized methods.

package multithreading;

import static java.lang.System.out;

public class NumberUtility {

boolean oddPrinted = false;

public synchronized void printOdd(int number) {

while (oddPrinted == true) {

try {

wait();   // waits until notified by even thread

} catch (InterruptedException e) {

e.printStackTrace();

}

}

out.println(“printOdd() ” + number);

oddPrinted = true;

notifyAll();  //notify all waiting threads

}

public synchronized void printEven(int number) {

while (oddPrinted == false) {

try {

wait();  //waits until notified by the odd thread

} catch (InterruptedException e) {

}

}

oddPrinted = false;

out.println(“printEven() ” + number);

notifyAll();  //notify all waiting threads

}

}

The output will be something like:

printOdd() 1

printEven() 2

printOdd() 3

printEven() 4

printOdd() 5

printEven() 6

printOdd() 7

printEven() 8

printOdd() 9

printEven() 10

Write a multi-threaded Java program in which, one thread generates odd numbers and write to a pipe and the second thread generates even numbers and write to another pipe, and a third thread receives the numbers from both the pipes and evaluates if the sum is multiples of 5

In Unix, a pipe (“|”) operator helps you to redirect output from one command to another.

PipedReader and PipedWriterclasses in java.io package helps you to do the same.

It helps you to redirect the read input into writer seamlessly.

In Unix, two different processes on different address spaces can communicate using pipe, but in java two threads on the JVM can communicate using Piped ByteStream/CharacterStream within the same process

(i.e same address space)

Here is the code snippet. The Writer threads responsible for writing odd and even numbers to the respective pipes.

package multithreading;

import java.io.IOException;

import java.io.PipedWriter;

public class NumberWriter extends Thread {

private PipedWriter writer;

private int maxNumber;

private boolean isEvenNumber;

public NumberWriter(PipedWriter writer, int maxNumber, boolean isEvenNumber) {

this.writer = writer;

this.maxNumber = maxNumber;

this.isEvenNumber = isEvenNumber;

}

public void run() {

int i = 1;

while (i <= maxNumber) {

try {

if (isEvenNumber && (i % 2) == 0) {

writer.write(i);

} else if (!isEvenNumber && i%2 != 0) {

writer.write(i);

}

++i;

} catch (IOException e) {

e.printStackTrace();

}

}

}

public static void main(String[] args) {

final int MAX_NUM = 10;

PipedWriter oddNumberWriter = new PipedWriter();

PipedWriter evenNumberWriter = new PipedWriter();

NumberWriter oddGen = new NumberWriter(oddNumberWriter, MAX_NUM, false);

NumberWriter evenGen = new NumberWriter(evenNumberWriter, MAX_NUM, true);

NumberReceiver receiver = new NumberReceiver(oddNumberWriter, evenNumberWriter);

oddGen.start();

evenGen.start();

receiver.start();

}

}

The receiver thread that listens to both odd and even number pipes and computes the sum. If the sum is a multiple of 5, it prints the numbers and the sum.

package multithreading;

import java.io.IOException;

import java.io.PipedReader;

import java.io.PipedWriter;

public class NumberReceiver extends Thread {

private PipedReader oddReader;

private PipedReader evenReader;

public NumberReceiver(PipedWriter oddWriter, PipedWriter evenWriter) {

try {

this.oddReader = new PipedReader(oddWriter);

this.evenReader = new PipedReader(evenWriter);

} catch (IOException e) {

e.printStackTrace();

}

}

public void run() {

int odd =0, even=0;

try {

while (odd != -1) {

odd = oddReader.read();

even = evenReader.read();

if ((odd + even) % 5 == 0) {

System.out.println(“match found ” + odd + ” + ” + even + ” = ” + (odd + even));

}

}

} catch (IOException e) {

System.exit(1);

}

}

}

The output will be something like:

match found 7 + 8 = 15

Can you give some examples of thread racing conditions you had experienced

  • Declaring variables in JSP pages are not thread-safe. The declared variables in JSP pages end-up as instance variables in the converted Servlets. <%! Calendar c = Calendar.getInstance(); %>
  • Decalring instance variables in Servlets is not thread safe, as Servlets are inherently multi-threaded and gets accessed by multiple-threads. Same is true for the Actionclasses in the struts framework.
  • Some of the Java standard library classes likeSimpleDateFormat is not thread-safe. Always check the API to see if a particular class is thread-safe. If a particular class or library is not therad-safe, you could do one of three things.

Provide your own wrapper class that decorates the third-party library with proper synchronization.

This is a typical use of the decorator design pattern.

Use an alternative library, which is thread-safe if available.

For example, Joda Time Library.

Use it in a thread-safe manner.

For example, you could use the SimpleDateFormat class as shown below within a ThreadLocal class.

Each thread will have its own instance of the SimpleDateFormat object.

public class DateFormatTest

{

//          anonymous inner class. Each thread will have its own copy

private final static ThreadLocal<SimpleDateFormat> shortDateFormat

=  new ThreadLocal<SimpleDateFormat>()

{

protected SimpleDateFormat initialValue()

{

return new SimpleDateFormat(“dd/MM/yyyy”);

}

};

public Date convert(String strDate)throws ParseException

{

//          get the SimpleDateFormat instance for this thread and parse the date string

Date d = shortDateFormat.get().parse(strDate);

return d;

}

}

  • The one that is very popular with the interviewers is writing the singleton classes that are not thread-safe.

Can a thread call a non-synchronized instance method of an Object when a synchronized method is being executed

Yes, a Non synchronized method can always be called without any problem. In fact Java does not do any check for a non-synchronized method. The Lock object check is performed only for synchronized methods/blocks. In case the method is not declared synchronized Jave will call even if you are playing with shared data. So you have to be careful while doing such thing. The decision of declaring a method as synchronized has to be based on critical section access. If your method does not access a critical section (shared resource or data structure) it need not be declared synchronized. Below is the example which demonstrates this, The Common class has two methods synchronizedMethod1() and method1() MyThread class is calling both the methods in separate threads,

public class Common {

public synchronized void synchronizedMethod1() {

System.out.println(“synchronizedMethod1 called”);

try {

Thread.sleep(1000);

} catch (InterruptedException e) {

e.printStackTrace();

}

System.out.println(“synchronizedMethod1 done”);

}

public void method1() {

System.out.println(“Method 1 called”);

try {

Thread.sleep(1000);

} catch (InterruptedException e) {

e.printStackTrace();

}

System.out.println(“Method 1 done”);

}

}

public class MyThread extends Thread {

private int id = 0;

private Common common;

public MyThread(String name, int no, Common object) {

super(name);

common = object;

id = no;

}

public void run() {

System.out.println(“Running Thread” + this.getName());

try {

if (id == 0) {

common.synchronizedMethod1();

} else {

common.method1();

}

} catch (Exception e) {

e.printStackTrace();

}

}

public static void main(String[] args) {

Common c = new Common();

MyThread t1 = new MyThread(“MyThread-1”, 0, c);

MyThread t2 = new MyThread(“MyThread-2”, 1, c);

t1.start();

t2.start();

}

}  

Here is the output of the program

Running ThreadMyThread-1

synchronizedMethod1 called

Running ThreadMyThread-2

Method 1 called

synchronizedMethod1 done

Method 1 done

This shows that method1() – is called even though the synchronizedMethod1() was in execution.