作者热门文章
- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
如果对象的非原始包含字段作为引用该字段对象的对象句柄传递,那么如果原始传递的字段被更新/更改,它是否容易被更改?
public class MutableDog
{
public String name;
public String color;
public MutableDog(String name, String color)
{
this.name = name;
this.color = color;
}
}
public class ImmutableDog // are fields of these objects truly safe from changing?
{
private final String name;
private final String color;
public ImmutableDog(MutableDog doggy)
{
this.name = doggy.name;
this.color = doggy.color;
}
public String getColor()
{
return this.color;
}
}
public static void main(String[] args)
{
MutableDog aMutableDog = new MutableDog("Courage", "Pink");
ImmutableDog anImmutableDog = new ImmutableDog(aMutableDog);
aMutableDog.color = "Pink/Black";
anImmutableDog.getColor().equals(aMutableDog.color); // true or false?
}
本质上,ImmutableDog
真的是不可变的吗?在示例中,使用了字符串。使用可变对象(例如 Collection
)会有所不同吗?
此问题是对 this 的回应回答。
最佳答案
ImmutableDog
确实是不可变的,即使它可以从可变对象接收字符串。这是因为 String
是不可变的。这也证明了不可变性的巨大好处之一 - 您可以传递不可变的对象,而不必担心它们会突然改变。
您可能认为可以通过设置 MutableDog
实例的字段来以某种方式更改 ImmutableDog
中的字段:
aMutableDog.color = "Pink/Black";
但是,"Pink/Black"
与此处分配给 ImmutableDog
的字符串实例不同,因此 ImmutableDog
不会改变.
另一方面,如果 ImmutableDog
有一个可变类型的字段,那么它就不再是真正的不可变了。
例如,这是相同的代码,但使用 StringBuilder
:
public class MutableDog
{
public StringBuilder name;
public StringBuilder color;
public MutableDog(StringBuilder name, StringBuilder color)
{
this.name = name;
this.color = color;
}
}
public class ImmutableDog // are fields of these objects truly safe from changing?
{
private final StringBuilder name;
private final StringBuilder color;
public ImmutableDog(MutableDog doggy)
{
this.name = doggy.name;
this.color = doggy.color;
}
public String getColor()
{
return this.color.toString();
}
}
public static void main(String[] args)
{
MutableDog aMutableDog = new MutableDog("Courage", "Pink");
ImmutableDog anImmutableDog = new ImmutableDog(aMutableDog);
aMutableDog.color.append(" and Black");
anImmutableDog.getColor().equals(aMutableDog.color);
}
现在,不可变的狗的颜色似乎会发生变化。您仍然可以通过在构造函数中复制字符串生成器来防御这种情况:
public ImmutableDog(MutableDog doggy)
{
this.name = new StringBuilder(doggy.name);
this.color = new StringBuilder(doggy.color);
}
但是,这仍然允许您(意外地)修改 ImmutableDog
类中的字符串构建器。
所以不要将可变类存储在不可变类中。 :)
关于java - 在 Java 中,是否将对象的非基元包含字段传递给作为对象句柄传递的方法,如果是这样,这会如何影响其可变性?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63717896/
我是一名优秀的程序员,十分优秀!