Map相关累积
google的guava包给map的操作提供了许多便捷的操作:
- Maps.difference ,对比map的区别点
Maps.difference
Maps.difference方法返回两个map中的区别项,此操作得到的值不会随着map的修改而改变。
/** * Computes the difference between two maps. This difference is an immutable snapshot of the state * of the maps at the time this method is called. It will never change, even if the maps change at * a later time. * * <p>Since this method uses {@code HashMap} instances internally, the keys of the supplied maps * must be well-behaved with respect to {@link Object#equals} and {@link Object#hashCode}. * * <p><b>Note:</b>If you only need to know whether two maps have the same mappings, call {@code * left.equals(right)} instead of this method. */
Maps.difference有两个重载方法,区别在于是否使用默认的相等对比方法。如果想要自己提供对比策略,可以在difference时提供策略类(继承了Equivalence类,并且重写doEquivalent和doHash方法)。
public static <K, V> MapDifference<K, V> difference(Map<? extends K, ? extends V> left, Map<? extends K, ? extends V> right);
public static <K, V> MapDifference<K, V> difference( Map<? extends K, ? extends V> left, Map<? extends K, ? extends V> right, Equivalence<? super V> valueEquivalence);
下为guava中实现difference的主要代码:
public static <K, V> MapDifference<K, V> difference(
Map<? extends K, ? extends V> left, Map<? extends K, ? extends V> right) {
if (left instanceof SortedMap) {
SortedMap<K, ? extends V> sortedLeft = (SortedMap<K, ? extends V>) left;
return difference(sortedLeft, right);
}
return difference(left, right, Equivalence.equals());
}
public static <K, V> MapDifference<K, V> difference(
Map<? extends K, ? extends V> left,
Map<? extends K, ? extends V> right,
Equivalence<? super V> valueEquivalence) {
Preconditions.checkNotNull(valueEquivalence);
Map<K, V> onlyOnLeft = newLinkedHashMap();
Map<K, V> onlyOnRight = new LinkedHashMap<>(right); // will whittle it down
Map<K, V> onBoth = newLinkedHashMap();
Map<K, MapDifference.ValueDifference<V>> differences = newLinkedHashMap();
doDifference(left, right, valueEquivalence, onlyOnLeft, onlyOnRight, onBoth, differences);
return new MapDifferenceImpl<>(onlyOnLeft, onlyOnRight, onBoth, differences);
}
private static <K, V> void doDifference(
Map<? extends K, ? extends V> left,
Map<? extends K, ? extends V> right,
Equivalence<? super V> valueEquivalence,
Map<K, V> onlyOnLeft,
Map<K, V> onlyOnRight,
Map<K, V> onBoth,
Map<K, MapDifference.ValueDifference<V>> differences) {
for (Entry<? extends K, ? extends V> entry : left.entrySet()) {
K leftKey = entry.getKey();
V leftValue = entry.getValue();
if (right.containsKey(leftKey)) {
V rightValue = onlyOnRight.remove(leftKey);
if (valueEquivalence.equivalent(leftValue, rightValue)) {
onBoth.put(leftKey, leftValue);
} else {
differences.put(leftKey, ValueDifferenceImpl.create(leftValue, rightValue));
}
} else {
onlyOnLeft.put(leftKey, leftValue);
}
}
}
例子