Java不可变对象如何回收,Java不可变对象

本文探讨了如何通过使用不可变对象来提升线程安全性,避免并发修改静态列表导致的问题。作者介绍了为何不可变对象如`AString`在多线程环境中无须同步,并通过`Guava`的`ImmutableList`实例展示了如何防止意外修改。关键教训是理解并应用原子性和一致性原则,尤其是在处理静态资源时。
摘要由CSDN通过智能技术生成

Nicole..

10

..自动线程安全,没有同步问题

当两个不同的线程修改同一对象的状态时,会发生并发问题.不可变对象无法修改,因此没有问题.

示例:A String.可以String毫无顾虑地传递两个线程,因为它们都不能以任何方式改变它.

不需要复制构造函数

...因为副本是改变它的唯一方法.每个"修改"操作的不可变对象的一种常见设计模式,用于制作副本然后对新对象执行操作.

复制构造函数通常用于要更改的对象,而不会影响原始对象.对于不可变对象,总是如此(根据定义).

在这种情况下String,所有方法和+操作符都返回新的Strings.

不需要克隆的实现

往上看.

当用作场时,不需要防御性地复制

从前我做过傻事.我在List中有一组枚举:

private static final List validStatuses;

static {

validStatuses = new ArrayList();

validStates.add(Status.OPEN);

validStates.add(Status.REOPENED);

validStates.add(Status.CLOSED);

}

此列表是从方法返回的:

public static List getAllStatuses() {

return validStates;

}

我检索了该列表,但只想在界面中显示打开状态:

List statuses = Status.getAllStatuses();

statuses.remove(Status.CLOSED);

很棒,它有效!等等,现在所有状态列表只显示那两个 - 即使页面刷新后!发生了什么?我修改了一个静态对象.哎呀.

我本可以在返回对象上使用防御性复制getAllStatuses.或者,我可以首先使用像Guava的ImmutableList这样的东西:

private static final List validStatuses =

ImmutableList.of(Status.OPEN, Status.REOPENED, Status.CLOSED);

然后当我做了一些愚蠢的事情:

List statuses = Status.getAllStatuses();

statuses.remove(Status.CLOSED); // Exception!

总是有"失败原子性"(Joshua Bloch使用的术语):如果一个不可变对象抛出一个异常,它就永远不会处于不受欢迎或不确定的状态.

因为永远不能修改类,所以通过修改发出的所有状态都是完整的限定对象(因为它们不能更改,所以它们必须始终处于合格状态才有用).异常不会发出新对象,因此您永远不会有不受欢迎或不确定的状态.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值