Java 通过改变映射的引用来更新映射的值是否是一种错误的做法?

Java 通过改变映射的引用来更新映射的值是否是一种错误的做法?,java,functional-programming,hashmap,immutability,Java,Functional Programming,Hashmap,Immutability,我正在处理的代码库中有类似的代码: Map<String, Map<Object, Integer>> mapOfMap = new HashMap<>(); Map<Object, Integer> mapA = mapOfMap.computeIfAbsent(keyParam, k -> new HashMap<>()); mapA.put(objectParam, mapA.getOrDefault(objectPara

我正在处理的代码库中有类似的代码:

Map<String, Map<Object, Integer>> mapOfMap = new HashMap<>();

Map<Object, Integer> mapA = mapOfMap.computeIfAbsent(keyParam, k -> new HashMap<>());
mapA.put(objectParam, mapA.getOrDefault(objectParam, 0) + 1);
Map-mapOfMap=newhashmap();
Map mapA=mapOfMap.computeIfAbsent(keyParam,k->new HashMap());
put(objectParam,mapA.getOrDefault(objectParam,0)+1);
这样,我们就更新了第一个映射中“keyParam”的值,而无需直接调用put()方法


我倾向于选择代码是显式的,并且通常编写对“put”的简单调用。然而,我想知道我是否想得太多了,这种简洁性是我们通过对象引用获得的吗?这是否可以用Java中类似的简洁方式编写,假装对象是不可变的?

可以,但在本例中不是

在这种情况下,代码大概知道它在做什么。它甚至可能被定义为对象是可变的。解决这个问题的唯一方法是复制值对象,对其进行变异,然后再次放置。在某些程序中,这可能会非常昂贵,而且我不确定这种样式是否真的更好,我不觉得它更可读或者总是不容易出错。这取决于你一般对不可变对象的信任程度

当事情发生了不应该发生的变异时,问题就出现了。但这与地图本身无关

例如:


在这种情况下,对一个被认为是不可变的列表的引用被传递到对其进行变异的代码部分,在这种情况下至少会导致内存泄漏。

存在一些冲突的变量名,这使得解析这应该演示的内容非常困难。
mapOfMap
mapOfMap
应该是相同的吗?在任何情况下,这段代码都不会显得异常;可变性没有什么奇怪的。方法
put()
computeifassent
(和
putIfAbsent()
)是完全不同的。如果用put替换计算,代码的含义将完全不同。在本例中,情况并非如此,因为这是一个处理空贴图的合成示例。很不清楚你想假装什么是不可变的,这些映射?@LouisWasserman讨论的问题是在映射中使用可变对象作为值是否是不好的风格。@Kayaman谢谢,我知道它们是不同的东西。我不是说用put替换计算。我说的更多的是在最后一行添加另一个“put”,以显示mapOfMap已经更新,而不是仅仅依赖于可变性。这不是惯用的代码。这只会让人困惑,而不会提高可读性。将可变对象作为值是一种不错的风格,但如果不小心,将可变对象作为键可能是危险的。带有
computeIfAbsent
oth的映射是惯用代码,因此不需要额外的put,也不需要担心可变性(除了正常的担心)。