Java: ThreadLocal用法

來源:互聯網
上載者:User

顧名思義,ThreadLocal是為了支援thread-local的變數,它有這樣的特點:

  1. 對於同一個線程來說,ThreadLocal是全域的,你可以在這個線程的任何地方得到這個ThreadLocal的值。比如在函數A中設定ThreadLocal的值,然後在函數B中得到這個值。
  2. 對於別的線程來說,ThreadLocal是局部的,你不能這樣做:線上程A中設定ThreadLocal的值,然後線上程B中得到這個值。

ThreadLocal類只有三個成員函數:

  • protected Object initialValue() – 返回ThreadLocal變數的初始值。在一線程中,如果在調用set()之前調用get()的時候,initialValue()就會被調用,而且也只會被調用一次。如果在調用get()之前已經調用過set()了,那麼initialValue()就不會被調用。
  • public Object get() – 得到這個ThreadLocal變數的值(對於當前線程的)。
  • public void set(Object value) – 設定這個ThreadLocal的變數的值(對於當前線程的)。

用處:

當你需要把一個單線程程式移植到多線程的環境的時候,你可以根據實際情況把一些全域變數用ThreadLocal封裝起來,從而實現安全執行緒。但是不要濫用ThreadLocal:你在函數A設定一個ThreadLocal,然後函數B中使用這個ThreadLocal,也就意味著,B依賴於A。

需要注意的事項:

從JDK的原始碼來看,在get的時候,是根據ThreadLocal的reference來找實際的值,那麼在set()和get()之間不要去改變ThreadLocal的reference,比如new一個新的ThreadLocal。

public T get() {    Thread t = Thread.currentThread();    ThreadLocalMap map = getMap(t);    if (map != null) {        ThreadLocalMap.Entry e = map.getEntry(this);        if (e != null)            return (T)e.value ;    }    return setInitialValue();}

一個錯誤的例子:在多線程環境下,如果調用順序是線程A調用setValue(oa),線程B調用setValue(ob),線程A調用getValue(),那麼將得到一個空值。因為tl的reference已經改變了。

public class ThreadLocalTest {    static ThreadLocal tl = null;        public static void setValue(Object o) {        tl = new  ThreadLocal();        tl.set(o);    }        public static Object getValue() {        return tl.get();    }}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.