java中的volatile vs threadLocal

时间:2016-10-06 15:01:00

标签: java multithreading volatile thread-local

让我们以SimpleDateFormat为例,因为它不是线程安全的。

我可以允许每个线程使用threadLocal拥有自己的SimpleDateFormat副本,如下所示:

 private static final ThreadLocal<SimpleDateFormat> formatter = new ThreadLocal<SimpleDateFormat>(){
    @Override
    protected SimpleDateFormat initialValue()
    {
        return new SimpleDateFormat("yyyyMMdd HHmm");
    }
};

但volatile关键字保证线程将拥有该变量的最新副本。所以我不能这样做:

volatile SimpleDateFormat myformatter;

并实现相同的线程安全性?

3 个答案:

答案 0 :(得分:4)

  

volatile关键字保证线程拥有变量的最新副本

只有 ,而不是其字段。

此外,* installing *source* package \u2018pbkrtest\u2019 ... ** package \u2018pbkrtest\u2019 successfully unpacked and MD5 sums checked ** R ** data ** inst ** preparing package for lazy loading ** help *** installing help indices converting help for package \u2018pbkrtest\u2019 finding HTML links ... done DATA-beets html DATA-budworm html KRmodcomp html finding level-2 HTML links ... done PBmodcomp html PBrefdist html getKR html get_ddf_Lb html model2restrictionMatrix html pbkrtest-internal html vcovAdj html ** building package indices ** installing vignettes ** testing if installed package can be loaded * DONE (pbkrtest) Making 'packages.html' ... done * installing *source* package \u2018car\u2019 ... ** package \u2018car\u2019 successfully unpacked and MD5 sums checked ** R ** data *** moving datasets to lazyload DB ** inst ** byte-compile and prepare package for lazy loading ** help *** installing help indices converting help for package \u2018car\u2019 finding HTML links ... done AMSsurvey html Adler html Angell html Anova html Anscombe html Baumann html Bfox html Blackmore html Boot html Boxplot html Burt html CanPop html Chile html Chirot html Contrasts html Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/Contrasts.Rd:68: missing file link \u2018contr.treatment\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/Contrasts.Rd:68: missing file link \u2018contr.sum\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/Contrasts.Rd:69: missing file link \u2018contr.helmert\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/Contrasts.Rd:69: missing file link \u2018contr.poly\u2019 Cowles html Davis html DavisThin html Depredations html Duncan html Ellipses html Ericksen html Florida html Freedman html Friendly html Ginzberg html Greene html Guyer html Hartnagel html Highway1 html KosteckiDillon html Leinhardt html LoBD html Mandel html Migration html Moore html Mroz html OBrienKaiser html Ornstein html Pottery html Prestige html Quartet html Robey html SLID html Sahlins html Salaries html ScatterplotSmoothers html Soils html States html Transact html TransformationAxes html UN html USPop html Vocab html WeightLoss html Womenlf html Wong html Wool html avPlots html bcPower html bootCase html boxCox html boxCoxVariable html boxTidwell html car-deprecated html car-internal html car-package html carWeb html ceresPlots html compareCoefs html crPlots html deltaMethod html densityPlot html dfbetaPlots html durbinWatsonTest html hccm html hist.boot html infIndexPlot html influencePlot html Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/influencePlot.Rd:62: missing file link \u2018cooks.distance\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/influencePlot.Rd:62: missing file link \u2018rstudent\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/influencePlot.Rd:63: missing file link \u2018hatvalues\u2019 invResPlot html invTranPlot html leveneTest html leveragePlots html linearHypothesis html logit html marginalModelPlot html mcPlots html ncvTest html outlierTest html panel.car html plot.powerTransform html powerTransform html qqPlot html Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/qqPlot.Rd:114: missing file link \u2018qqplot\u2019 Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/qqPlot.Rd:115: missing file link \u2018qqline\u2019 recode html regLine html residualPlots html scatter3d html scatterplot html scatterplotMatrix html showLabels html sigmaHat html skewPower html some html Rd warning: /tmp/RtmpHIzBAB/R.INSTALL69be5853f984/car/man/some.Rd:47: missing file link \u2018tail\u2019 spreadLevelPlot html subsets html symbox html testTransform html vif html wcrossprod html which.names html ** building package indices ** installing vignettes ** testing if installed package can be loaded * DONE (car) Making 'packages.html' ... done The downloaded source packages are in \u2018/tmp/RtmpeVpYkV/downloaded_packages\u2019 仅在您需要更改变量值时才有用。在您的使用案例中,public void doRequest() { String url=getURL(); final JSONObject[] mJsonWeather = {null}; JsonObjectRequest jsonObjectRequest=new JsonObjectRequest(Request.Method.GET, url, null, new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject response) { mJsonWeather[0]=response; Weather weather = getJsonWeatherData(jsonObjectWeather); setWeatherobj(weather); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { Log.i("Error","can't process json result"); } }); MySingleton.getInstance(mContext.getApplicationContext()).addToRequestQue(jsonObjectRequest); return mJsonWeather[0]; } 看起来更合适:

volatile

这也保证了你将获得变量的最新值 - 因为它只能被赋值一次,而final可以保证在类完全加载后可见性。

但这并不是private static final SimpleDateFormat format = ... 无法保证线程安全的原因:它具有可变状态,用于在格式化日期时存储中间值。

如果一个线程调用static final而另一个线程也在同一个SimpleDateFormat实例的format方法中,则这些中间变量会不可预测地被踩踏,从而导致线程之间的干扰,从而不可预测的输出。

当另一个线程读/写时,这些中间变量的值是否是最新的并不重要 - 它们的更新可以散布。

简而言之,format不会阻止线程干扰,因此不适合替代SimpleDateFormatter

答案 1 :(得分:1)

ThreadLocal是一种工具,它使线程拥有自己的对象本地副本。 ThreadLocals最好与在线程限制的线程安全策略中可以线程安全的对象一起使用(即使对于许多不是“线程安全”的对象,只要没有引用,线程安全使用仍然是可能的他们从限制线程泄漏出来。 ThreadLocals无法帮助在实例化它们的线程之外共享的可变对象的线程安全使用。

volatile关键字用于通过可由许多不同线程访问的变量提供弱形式的线程安全性。一个关键的区别是ThreadLocals通常不被多个线程访问。

一般来说,线程安全需要可见性(变量的最新更新应该对其他线程可见)和互斥(状态转换必须是原子的,以便不能观察到状态不一致)。 Volatile与Java内存模型一起使用以保证变量可见,但它不提供任何形式的互斥,因此不为对象中的状态转换提供原子性。

由于volatileThreadLocal如此不同,因此确实没有一种情况可以替代另一种情况。

答案 2 :(得分:0)

您与volatile无法实现相同的线程安全性,因为SimpleDateFormat的相同实例将在不同的线程中使用。