Java 中 List<Integer, Integer> 个元素的总和
Sum of List<Integer, Integer> elements in Java
我有一个 ArrayList
,其中包含一些 Integer values
作为 Pairs
。我想对左侧元素相同的列表的 right
个元素求和。
例如,输入数组列表将包含:
final List<Pair<Integer, Integer>> a = new ArrayList<>();
a.add(new Pair<>(1, 1));
a.add(new Pair<>(2, 1));
a.add(new Pair<>(2, 3));
New ArrayList should contain:
如下图:
(公共左值,左值相同的所有右值之和)
1, 1
2, 4
我编写的代码没有 return 有效值:
for (int i=0; i< a.size(); i++){
//need help here
}
编辑:我想要重复的对,所以 HashMap 不起作用。
抱歉进行了编辑。
你的问题是你只在你的循环中添加了两个元素,这两个元素适用于 1 但不适用于 2。相反,你应该使用一个映射,其中键是第一个数字(在你的情况下是 1 或 2)和值是总和。
然后独立循环两个列表,获取左侧数字的当前值,将右侧数字添加到它,并将结果放回地图中。如果还没有值,您会假设为 0。
像这样:
Map<Integer, Integer> sums = new HashMap<>();
for( Pair<> p : a ) {
Integer sum = sums.get(p.left);
if( sum == null ) {
sums.put( p.left, p.right ); //nothing there yet, so just add the first value
} else {
sums.put( p.left, sum + p.right ); //add to the existing sum
}
}
//do the same for b
最后遍历地图并根据需要构建新的配对列表。
如果您还需要获取原始对,请创建一个容器对象用作包含总和的值以及对该总和做出贡献的对列表。我会把代码留给你作为练习。
这是未经测试的代码,但应该能让您有所了解
HashMap<Integer, Integer> result = new HashMap<Integer, Integer>();
List<Pair<Integer, Integer>> list = new ArrayList<Pair<Integer, Integer>>();
for (Pair p : a)
if (result.containsValue(p.left))
result.put(p.left, p.right +result.get(p.left)); // add if existing
else
result.put(p.left, p.right); // assign if not existing
for (Pair p : b)
if (result.containsValue(p.left))
result.put(p.left, p.right +result.get(p.left));
else
result.put(p.left, p.right);
p.s.(根据评论):将新对添加到列表:
for (Pair p : a)
list.add(new Pair(p.left, result.get(p.left)));
for (Pair p : b)
list.add(new Pair(p.left, result.get(p.left)));
使用org.springframework.util.MultiValueMap:
List<Pair<Integer, Integer>> result = new ArrayList<>();
a.addAll(b); //now there is only one list
//key -> Integer, value -> List<Integer>
MultiValueMap<Integer, Integer> values = new LinkedMultiValueMap<Integer, Integer>();
for (Pair p : a)
values.add(p.left, p.right);
for (Integer key : values.keySet()) {
Integer sum = 0;
for (Integer right : values.get(key))
sum += right;
result.add(new Pair(key, sum));
}
您似乎需要一些黑客技术 HashMap
,它将对值求和而不是替换它们:
class SummingMap extends HashMap<Integer, Integer> {
@Override
public Integer put(Integer key, Integer value) {
Integer oldResult = get(key);
return super.put(key, value + (oldResult == null ? 0 : oldResult));
}
}
如果您希望条目按关键字排序,您应该使用某种 SortedMap
,例如 TreeMap
:
class SummingMap extends TreeMap<Integer, Integer> {
... // the same code as above
我有一个 ArrayList
,其中包含一些 Integer values
作为 Pairs
。我想对左侧元素相同的列表的 right
个元素求和。
例如,输入数组列表将包含:
final List<Pair<Integer, Integer>> a = new ArrayList<>();
a.add(new Pair<>(1, 1));
a.add(new Pair<>(2, 1));
a.add(new Pair<>(2, 3));
New ArrayList should contain:
如下图:
(公共左值,左值相同的所有右值之和)
1, 1
2, 4
我编写的代码没有 return 有效值:
for (int i=0; i< a.size(); i++){
//need help here
}
编辑:我想要重复的对,所以 HashMap 不起作用。
抱歉进行了编辑。
你的问题是你只在你的循环中添加了两个元素,这两个元素适用于 1 但不适用于 2。相反,你应该使用一个映射,其中键是第一个数字(在你的情况下是 1 或 2)和值是总和。
然后独立循环两个列表,获取左侧数字的当前值,将右侧数字添加到它,并将结果放回地图中。如果还没有值,您会假设为 0。
像这样:
Map<Integer, Integer> sums = new HashMap<>();
for( Pair<> p : a ) {
Integer sum = sums.get(p.left);
if( sum == null ) {
sums.put( p.left, p.right ); //nothing there yet, so just add the first value
} else {
sums.put( p.left, sum + p.right ); //add to the existing sum
}
}
//do the same for b
最后遍历地图并根据需要构建新的配对列表。
如果您还需要获取原始对,请创建一个容器对象用作包含总和的值以及对该总和做出贡献的对列表。我会把代码留给你作为练习。
这是未经测试的代码,但应该能让您有所了解
HashMap<Integer, Integer> result = new HashMap<Integer, Integer>();
List<Pair<Integer, Integer>> list = new ArrayList<Pair<Integer, Integer>>();
for (Pair p : a)
if (result.containsValue(p.left))
result.put(p.left, p.right +result.get(p.left)); // add if existing
else
result.put(p.left, p.right); // assign if not existing
for (Pair p : b)
if (result.containsValue(p.left))
result.put(p.left, p.right +result.get(p.left));
else
result.put(p.left, p.right);
p.s.(根据评论):将新对添加到列表:
for (Pair p : a)
list.add(new Pair(p.left, result.get(p.left)));
for (Pair p : b)
list.add(new Pair(p.left, result.get(p.left)));
使用org.springframework.util.MultiValueMap:
List<Pair<Integer, Integer>> result = new ArrayList<>();
a.addAll(b); //now there is only one list
//key -> Integer, value -> List<Integer>
MultiValueMap<Integer, Integer> values = new LinkedMultiValueMap<Integer, Integer>();
for (Pair p : a)
values.add(p.left, p.right);
for (Integer key : values.keySet()) {
Integer sum = 0;
for (Integer right : values.get(key))
sum += right;
result.add(new Pair(key, sum));
}
您似乎需要一些黑客技术 HashMap
,它将对值求和而不是替换它们:
class SummingMap extends HashMap<Integer, Integer> {
@Override
public Integer put(Integer key, Integer value) {
Integer oldResult = get(key);
return super.put(key, value + (oldResult == null ? 0 : oldResult));
}
}
如果您希望条目按关键字排序,您应该使用某种 SortedMap
,例如 TreeMap
:
class SummingMap extends TreeMap<Integer, Integer> {
... // the same code as above