java Hamcrest 平等集合

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1960971/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-29 18:43:41  来源:igfitidea点击:

Hamcrest equal collections

javaunit-testingjunitasserthamcrest

提问by Andrey Minogin

Is there a matcher in Hamcrest to compare collections for equality? There is containsand containsInAnyOrderbut I need equalsnot bound to concrete collection type. E.g. I cannot compare Arrays.asList and Map.values with Hamcrest equals.

Hamcrest 中是否有匹配器来比较集合的相等性?有contains并且containsInAnyOrder但我不需要equals绑定到具体的集合类型。例如,我无法将 Arrays.asList 和 Map.values 与 Hamcrest 进行比较equals

Thanks in advance!

提前致谢!

采纳答案by skaffman

I cannot compare Arrays.asList and Map.values with Hamcrest equals.

我无法将 Arrays.asList 和 Map.values 与 Hamcrest 相等。

This is because of hamcrest's over-zealous type signatures. You cando this equality comparison, but you need to cast the Listobject to Collectionbefore it'll compile.

这是因为 hamcrest 过于热情的类型签名。您可以进行此相等比较,但您需要在编译之前将List对象Collection强制转换为。

I often have to do casting with Hamcrest, which feels wrong, but it's the only way to get it to compile sometimes.

我经常不得不用 Hamcrest 进行转换,这感觉不对,但有时这是让它编译的唯一方法。

回答by Mark

Casting to a Collection may work, but it makes some assumptions about the underlying Collection implementations (e.g., order?). A more general approach would be to write your own matcher.

强制转换为 Collection 可能有效,但它对底层 Collection 实现做出了一些假设(例如,顺序?)。更通用的方法是编写自己的匹配器。

Here's a nearly complete matcher implementation that does what you want (you'll need to fill in the imports and describeTo method). Note that this implementation requires all elements of two collections to be equal, but not necessarily in the same order.

这是一个几乎完整的匹配器实现,可以满足您的需求(您需要填写 import 和 describeTo 方法)。请注意,此实现要求两个集合的所有元素都相等,但顺序不一定相同。

public class IsCollectionOf<T> extends TypeSafeMatcher<Collection<T>> {
    private final Collection<T> expected;
    public IsCollectionOf(Collection<T> expected) {
        this.expected = expected;
    }
    public boolean matchesSafely(Collection<T> given) {
        List<T> tmp = new ArrayList<T>(expected);
        for (T t : given) {
            if (!tmp.remove(t)) {
                return false;
            }
        return tmp.isEmpty();
    }
    // describeTo here
    public static <T> Matcher<Collection<T>> ofItems(T... items) {
        return new IsCollectionOf<T>(Arrays.asList(items));
    }
}

回答by Hans-Peter St?rr

If you have trouble with the equals method of the collections implementation, you might also first copy the collections:

如果您在使用集合实现的 equals 方法时遇到问题,您也可以先复制集合:

assertThat( new ArrayList<Whatever>(actual), equalTo( new ArrayList<Whatever>(expected) );

Also the following might work:

以下也可能有效:

assertThat(actual, both(everyItem(isIn(expected))).and(containsInAnyOrder(expected)));