java - 实现线程时,使用不可变对象(immutable对象)比使用可变对象更好吗?

标签 java multithreading thread-safety

我目前正在学习 Java 中的线程,从我读到的内容来看,实现它们并不是让您的代码线程安全那么重要的问题。这让我想到了我的问题:我是否应该尽可能使用不可变对象(immutable对象)来确保我防止并发错误?

我读过关于何时使用可变对象的不同意见,包括:

If immutable objects are good, why do people keep creating mutable objects? (Programmers.SE)

for large and/or complex objects, creating a new copy of the object for every single change can be very costly and/or tedious. And for objects with a distinct identity, changing an existing objects is much more simple and intuitive than creating a new, modified copy of it.

Immutable Objects (Java Tutorials)

The impact of object creation is often overestimated, and can be offset by some of the efficiencies associated with immutable objects. These include decreased overhead due to garbage collection, and the elimination of code needed to protect mutable objects from corruption.

那么,在实现线程的时候有没有最佳实践呢?如果可能,我是否应该始终尝试使用不可变对象(immutable对象)?

最佳答案

使用真正不可变的对象(没有包含对可变类的引用的字段)是线程安全的,在实际可行时使用它们是一个好习惯,但不可变性是否可行取决于具体情况;例如,一些工具包需要 setter 或字段注入(inject),因此不能与不可变对象(immutable对象)一起使用。不变性通常是 Value Object 模式中最实用的,其中对象没有任何特别复杂的行为,并且基本上封装了一个可清楚描述的值(String,原语包装器,Guava 的 Immutable* 集合)。

一般来说,只要可行,我都会尝试使具有简单字段的对象不可变,而且我发现从默认值开始是有帮助的,因为不可变对象(immutable对象)是最安全的,并且只有在有特定原因需要它们时才使用增变器。

同样,如果您要依赖类的不变性来实现线程安全之类的功能,通常应该将类声明为 final 以避免各种麻烦。我并没有坚持所有类都必须是 abstractfinal,但是 final 可实例化类是一个很好的默认值。

关于java - 实现线程时,使用不可变对象(immutable对象)比使用可变对象更好吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19277711/

相关文章:

java - 如何阻止控制台在 Eclipse 中自动弹出

java - JFreeChart DateTickUnit 无法正常工作

java - 具有无界队列的 ThreadPoolExecutor 不创建新线程

c++ - 包括通过套接字监听的线程中断

java - 线程在单击按钮时开始,并在单击另一个按钮时结束线程

java - 为什么 Java 的 String 有方法 length() 而不是属性 length(像数组一样?)

c++ - boost::mutex 不能帮助避免 C++ 程序中的竞争条件?

python - Python如何连续填充子进程的多个线程?

c++ - 为什么无法通过 Call-by-Value 将 mutex 传递给 function?

java - 为什么我不应该在类的构造函数中使用 Thread.start()?