如何在Java中使局部变量不具备线程安全性?

huangapple go评论64阅读模式
英文:

How can a local variable become not thread safe in Java?

问题

以下是翻译好的内容:

我正在学习Java多线程编程,并阅读了以下语句:

> 局部变量始终是线程安全的。但请记住,局部变量指向的对象可能并非如此。如果对象是在方法内部实例化的并且从未逃逸,那就不会有问题。仅仅因为将共享对象分配给局部引用,并不意味着该对象自动变为线程安全。

public class SimpleHttpServlet extends HttpServlet {

 

  protected void Test() {

    // How can `object' become not thread safe
    SomeClass object= new SomeClass ();

  }
}

在这个例子中,object 如何变得不是线程安全的?

请您举一个例子,说明局部变量在某些情况下可能不是线程安全的原因。

英文:

I am learning Java multi threading and I read the following statement :

> Local variables are always thread safe. Keep in mind though, that the object a local variable points to, may not be so. If the object was
> instantiated inside the method, and never escapes, there will be no
> problem. Just because you assign a shared object to a local reference,
> does not mean that object automatically becomes thread safe.

public class SimpleHttpServlet extends HttpServlet {

 

  protected void Test() {

    // How can `object' become not thread safe
    SomeClass object= new SomeClass ();

  }
}

In this example how can object become not thread safe ?

Can you please explain with an example a scenario where local variable can be not thread safe and why ?

答案1

得分: 1

正如引用的文本本身所说,object 本身(即局部变量)是线程安全的。

您可以依赖于这样一个事实:没有外部因素(即没有其他线程)会更改该变量引用的内容。

然而object 引用的那个对象(由 new SomeClass() 创建的对象)可能会被其他线程操纵,如果对它的引用以某种方式逃逸。例如,如果您执行了类似 myGlobalList.add(object) 的操作,并且 myGlobalList 可被其他线程访问,那么另一个线程可能会获取该对象并在其上调用 setFoo,这可能会对您的代码产生意外影响。

这种“其他线程能够访问该对象”的情况被称为“逃逸”,即您的对象逃逸。

在您过于简化的示例中,这种情况并不会发生。您没有将对该对象的引用存储在其他任何地方,因此它当然会保持线程安全。

英文:

As the quoted text itself says object itself (i.e. the local variable) is thread safe.

You can rely on the fact that no outside factor (i.e. no other thread) changes what this variable references.

However the object that object references (the one created by new SomeClass()) could be manipulated by other threads if a reference to it somehow escapes. For example if you did something like myGlobalList.add(object) and myGlobalList was accessible to other threads, then another thread could get the object back and call setFoo on it, which might have unexpected effects on your code.

That "other threads being able to access the object" is called "escaping", i.e. your object escapes.

In your overly simplified example this doesn't happen. You don't store a reference to that object anywhere else, so it will of course stay thread safe.

huangapple
  • 本文由 发表于 2020年10月7日 17:47:31
  • 转载请务必保留本文链接:https://go.coder-hub.com/64241447.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定