2014-03-28 39 views
5

我想測試一個集合是否有toString()方法返回一個特定字符串的項目。我嘗試使用優秀的Hamcrest匹配類來做到這一點,通過組合包含Matchers.hasToString,但不知何故,其Matchers.contains不能匹配項目,即使它存在於集合中。Hamcrest Matchers.contains matcher not working(?)

下面是一個例子:

class Item { 

    private String name; 

    public Item(String name){ 
     this.name = name; 
    } 

    public String toString(){ 
     return name; 
    } 
} 

// here's a sample collection, with the desired item added in the end 
Collection<Item> items = new LinkedList<Item>(){{ 
    add(new Item("a")); 
    add(new Item("b")); 
    add(new Item("c")); 
}}; 

Assert.assertThat(items, Matchers.contains(Matchers.hasToString("c"))); 

上述說法並不成功。這裏的消息:

java.lang.AssertionError: 
Expected: iterable containing [with toString() "c"] 
    but: item 0: toString() was "a" 
    at org.hamcrest.MatcherAssert.assertThat(MatcherAssert.java:20) 
    at org.junit.Assert.assertThat(Assert.java:865) 
    at org.junit.Assert.assertThat(Assert.java:832) 

它看起來像Matchers.contains匹配試圖遍歷列表,但Matchers.hasToString匹配的第一個項目失敗和迭代的其餘部分無效。 Matchers.contains的Hamcrest javadoc說:

「爲Iterables創建一個匹配器,匹配時檢查Iterable上的單個遍將產生滿足指定匹配器的單個項目。對於正匹配,檢查的迭代只能產生一個item「

我做錯了什麼?

回答

14

我認爲你正在尋找Matchers.hasItem(..)

Assert.assertThat(items, Matchers.hasItem(Matchers.hasToString("c"))); 

其中規定

Creates a matcher for Iterables that only matches when a single pass over the examined Iterable yields at least one item that is matched by the specified itemMatcher . Whilst matching, the traversal of the examined Iterable will stop as soon as a matching item is found.

Matchers.contains,如你所說,

Creates a matcher for Iterables that matches when a single pass over the examined Iterable yields a single item that satisfies the specified matcher. For a positive match, the examined iterable must only yield one item.

在我看來,像在說應該只有Iterable中的一個元素。

+0

索蒂里奧斯,我試過hasItem,卻得到了一個編譯器錯誤:在類的方法assertThat(T,匹配器)斷言是不適用的參數(?收藏,匹配器<可迭代<超級對象>>) – JulioAragao

+0

@ JulioAragao我按照原樣複製了示例代碼,並用'hasItem'替換了'contains'。 –

+0

是的,我想你是對的@Sotirios。我改變了由包含匹配器迭代的列表中的順序,以便首先出現「c」,但即使如此也不會通過。我將調查爲什麼我有這個編譯問題,但我認爲你已經明確了它。謝謝! – JulioAragao