Search code examples
javamultithreadingconcurrency

Using ThreadLocal vs Atomic


According to ThreadLocal's javadoc, it sounds like its a thread-specific container for 1+ atomic fields.

Is the purpose of ThreadLocal to represent all the atomic fields for a single Thread, or is it to just provided a convenience container when you have multiple Atomic* instances that need to be logically grouped together?

I guess I'm wondering why I would ever want to use a ThreadLocal instead of, say, an AtomicLong or AtomicInteger? Thanks in advance!


Solution

  • The purpose of ThreadLocal is that the fields do not have to be atomic -- there is no need to synchronize their values with centralized memory. They are thread-local and only exist in the threads local memory storage.

    Why would I ever want to use a ThreadLocal instead of, say, an AtomicLong or AtomicInteger?

    ThreadLocal is very useful for storing a per-thread copy of something. For example a SimpleDateFormat which is unfortunately not reentrant.

    private final ThreadLocal<DateFormat> threadLocal =
            new ThreadLocal<DateFormat>() {
        @Override
        protected DateFormat initialValue() {
            return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSSSSS");
        }
    };
    ...
    // get one that is per-thread
    DateFormat dateFormat = threadLocal.get();
    

    This is a useful pattern because then we don't have to synchronize on it or worry about any volatile or other atomic operations that have memory barriers.

    One caveat is that ThreadLocal variables often are detected as memory leaks since they are only freed when the thread is reaped which can cause problems with web container class loaders.