Thread local

  1. Thread local class provides thread local variables.
  2. Thread local class maintains values per thread basis.
  3. Each thread local object maintains a separate value like user id, transaction id etc for each thread that access the object.
  4. Thread can access its local value, can manipulate its value and even can remove its value.
  5. In every part of the code which is execute by the Thread we can access its local variable.
  6. Example : Consider a servlet which invokes some business methods, we have a requirement to generate a unique transaction ID for each and every request and we have to pass this transaction id to the business methods. For this requirement we can use thread local to maintain a separate transaction id for every request i.e for every thread.
  7. Thread local class introduced in java 1.2 version and enhanced in 1.5 version
  8. Thread local can be associated with thread scope.
  9. Total code with is executed by the thread has access to the corresponding thread local variable.
  10. A thread can access its own local variables and can’t access other threads local variable.
  11. Once thread entered into dead state all its local variables are by default eligible for Garbage collection.

Constructor :

ThreadLocal tl = new ThreadLocal();
• creates a new ThreadLocal variable

Methods :

• Object get()
Returns the value of thread local variable associated with current thread.

• Object initialValue()
Returns initial value of thread local variable associated with current thread.
The default implementation of this method returns null
To customize our own initial value we have to override this method

• void set(Object newValue)
To set a new value

• void remove()
To remove the value of Thread local variable associated with current Thread.
It is newly added method in java 1.5 version.
After removal if we are trying to access, it will be reinitialized once again by invoking its initial value method.

Example1 :

package com.demo11;

public class ThreadLocalDemo1 {
	public static void main(String[] args) {
		ThreadLocal tl = new ThreadLocal();
		System.out.println(tl.get());
		tl.set("Tyson");
		System.out.println(tl.get());
		tl.remove();
		System.out.println(tl.get());
	}
}

Overriding of initial value method of Thread Local

public class ThreadLocalDemo2 {
	public static void main(String[] args) {
		ThreadLocal tl = new ThreadLocal() {
			public Object initialValue() {
				return "Justin";
			}
		};
		System.out.println(tl.get());
		tl.set("Tyson");
		System.out.println(tl.get());
		tl.remove();
		System.out.println(tl.get());
	}
}

Example of ThreadLocal in Use :

public class ThreadLocalDemo3 {
	public static void main(String[] args) throws InterruptedException {
		Temp x = new Temp();
		Thread t1 = new Thread(x,"ThreadA");
		Thread t2 = new Thread(x,"ThreadB");
		t1.start();
		t1.join();
		t2.start();
	}
}
class Temp implements Runnable{
	int x;
	ThreadLocal y = new ThreadLocal();

	@Override
	public void run() {
		if(Thread.currentThread().getName().equalsIgnoreCase("ThreadA")) {
			x = 100;
			y.set(100);
		}
		System.out.println("Thread Name "+Thread.currentThread().getName()+" Int Value :"+x+" Thread Local Value : "+y.get());
	}
}

A Separate Thread Id for every Thread can be implemented using Thread Local

public class ThreadLocalDemo4 {
	public static void main(String[] args) {
		CustomerThread c1 = new CustomerThread("Thread A");
		CustomerThread c2 = new CustomerThread("Thread B");
		CustomerThread c3 = new CustomerThread("Thread C");
		CustomerThread c4 = new CustomerThread("Thread D");
		c1.start();
		c2.start();
		c3.start();
		c4.start();
	}
}

class CustomerThread extends Thread{
	static Integer custId=0;
	public static ThreadLocal th1 = new ThreadLocal() {
		protected Integer initialValue() {
			return ++custId;
		}
	};
	CustomerThread(String name){
		super(name);
	}
	
	public void run() {
		System.out.println(Thread.currentThread().getName()+" executing with id "+th1.get());
	}
}

ThreadLocal Vs Inheritance (InheritableThreadLocal class)

  • Parent Threads ThreadLocal variable by default not available to the child thread, if we want to make parent threads ThreadLocal variable value available to the child thread then we shlould go for InheritableThreadLocal class.
  • By default child threads value is exactly same as parent Threads value but we can provide customized value for child Thread by overriding ChildValueMethod.
  • InheritableThreadLocal is the child class of ThreadLocal and Hence all methods present in thread local by default available to InheritableThreadLocal.
  • In Addition to this method it contains only one method
    public Object childValue(Object parentValue)
public class InheritableThreadLocalDemo1 {
	public static void main(String[] args) {
		new ParentThread().start();
	}
}
class ParentThread extends Thread{
	static ThreadLocal tl = new ThreadLocal();
	static InheritableThreadLocal itl = new InheritableThreadLocal();
	public void run() {
		tl.set("Parent Value");
		itl.set("Parent Value");
		new ChildThread().start();
	}
}
class ChildThread extends Thread{
	public void run() {
		System.out.println("Thread Local Value : "+ParentThread.tl.get());
		System.out.println("Inheritable Thread Local Value : "+ParentThread.itl.get());
	}
}

Leave a Comment