TheThreadLocalclass in Java enables you to create variables that can only be read and written by the same thread. Thus, even if two threads are executing the same code, and the code has a reference to aThreadLocalvariable, then the two threads cannot see each other'sThreadLocalvariables.

Creating a ThreadLocal

Here is a code example that shows how to create aThreadLocalvariable:

private ThreadLocal myThreadLocal = new ThreadLocal();

As you can see, you instantiate a newThreadLocalobject. This only needs to be done once per thread. Even if different threads execute the same code which accesses aThreadLococal, each thread will see only its ownThreadLocalinstance. Even if two different threads set different values on the sameThreadLocalobject, they cannot see each other's values.

Accessing a ThreadLocal

Once aThreadLocalhas been created you can set the value to be stored in it like this:

myThreadLocal.set("A thread local value");

You read the value stored in aThreadLocallike this:

String threadLocalValue = (String) myThreadLocal.get();

Theget()method returns anObjectand theset()method takes anObjectas parameter.

Generic ThreadLocal

You can create a genericThreadLocalso that you do not have to typecast the value returned byget(). Here is a genericThreadLocalexample:

private ThreadLocal
<
String
>
 myThreadLocal = new ThreadLocal
<
String
>
();

Now you can only store strings in theThreadLocalinstance. Additionally, you do not need to typecast the value obtained from theThreadLocal:

myThreadLocal.set("Hello ThreadLocal");

String threadLocalValue = myThreadLocal.get();

Initial ThreadLocal Value

Since values set on aThreadLocalobject only are visible to the thread who set the value, no thread can set an initial value on aThreadLocalusingset()which is visible to all threads.

Instead you can specify an initial value for aThreadLocalobject by subclassingThreadLocaland overriding theinitialValue()method. Here is how that looks:

private ThreadLocal myThreadLocal = new ThreadLocal
<
String
>
() {
    @Override protected String initialValue() {
        return "This is the initial value";
    }
};

Now all threads will see the same initial value when callingget()before having calledset().

Full ThreadLocal Example

Here is a fully runnable JavaThreadLocalexample:

public class ThreadLocalExample {


    public static class MyRunnable implements Runnable {

        private ThreadLocal
<
Integer
>
 threadLocal =
               new ThreadLocal
<
Integer
>
();

        @Override
        public void run() {
            threadLocal.set( (int) (Math.random() * 100D) );

            try {
                Thread.sleep(2000);
            } catch (InterruptedException e) {
            }

            System.out.println(threadLocal.get());
        }
    }


    public static void main(String[] args) {
        MyRunnable sharedRunnableInstance = new MyRunnable();

        Thread thread1 = new Thread(sharedRunnableInstance);
        Thread thread2 = new Thread(sharedRunnableInstance);

        thread1.start();
        thread2.start();

        thread1.join(); //wait for thread 1 to terminate
        thread2.join(); //wait for thread 2 to terminate
    }

}

This example creates a singleMyRunnableinstance which is passed to two different threads. Both threads execute therun()method, and thus sets different values on theThreadLocalinstance. If the access to theset()call had been synchronized, and it hadnotbeen aThreadLocalobject, the second thread would have overridden the value set by the first thread.

However, since itisaThreadLocalobject then the two threads cannot see each other's values. Thus, they set and get different values.

InheritableThreadLocal

TheInheritableThreadLocalclass is a subclass ofThreadLocal. Instead of each thread having its own value inside aThreadLocal, theInheritableThreadLocalgrants access to values to a thread and all child threads created by that thread.

results matching ""

    No results matching ""