Why are thread-local variables used?

The ThreadLocal class represents a storage of thread-local variables. In usage, it is similar to a standard wrapper around a value, with methods like get(), set(), and remove()for accessing it, and an additional factory method ThreadLocal.withInitial() for setting a default value.

The difference between a thread-local variable and a regular variable is that ThreadLocal stores a separate independent copy of the value for each thread that uses it. This makes working with such a variable thread-safe.

In simpler terms, a ThreadLocal object doesn&t store just one value but rather acts like a hash table of thread➝value, accessing the value corresponding to the current thread upon use.

The first, most obvious use case is for data that directly relates to the thread, a defined user "thread context." Below is a screenshot showing such usage: ThreadId.get() will return the ordinal number of the current thread.

Another scenario where thread-local variables can be useful is in caching read-only data in a multithreaded environment without costly synchronization.

Besides the usual ThreadLocal, the standard library includes an extension, InheritableThreadLocal. This class "inherits" the value—initially taking it from the thread that is the parent of the current thread.
Why are thread-local variables used?