2016-12-17 41 views
0

我想在android應用程序中進行搜索自動完成功能。有一系列商業名稱和列表業務類型,我將它們放入一個數組列表中,根據模糊搜索算法進行評分,然後根據搜索詞的分數對列表進行排序。我希望獲得與企業名稱相同的業務類型首先出現。我包裹業務和BusinessType的情況下,在這個類,因爲它們是得分,添加到列表中,然後排序:排序ArrayList:比較方法違反其總合約

public class SearchMatch<T extends NameMatcher> implements Comparable<SearchMatch> { 

    public T data; 
    public int score; 

    public SearchMatch(T data, int score) { 
     this.data = data; 
     this.score = score; 
    } 


    @Override 
    public int compareTo(SearchMatch o) { 
     if(this.score == o.score && this.data instanceof BusinessType 
      && o.data instanceof Business){ 
      return -1; 
     } 
     return o.score - this.score; 
    } 
} 

...但是這是行不通的。我得到一個「比較方法違反其總合同」。來自Collections.sort - 在logcat中沒有別的。

我不能看到它有什麼問題或它如何違反傳遞性(來自其他類似的帖子)。奇怪的是,如果我返回1而不是-1我沒有得到錯誤,但我得到了錯誤的偏好順序。

感謝

解決

public class SearchMatch<T extends NameMatcher> implements  Comparable<SearchMatch> { 

public final T data; 
public final int score; 

public SearchMatch(final T data,final int score) { 
    this.data = data; 
    this.score = score; 
} 


@Override 
public int compareTo(SearchMatch o) { 
    if(this.score == o.score && this.data instanceof BusinessType 
     && o.data instanceof Business){ 
     return -1; 
    } 

    if(this.score == o.score && this.data instanceof Business 
     && o.data instanceof BusinessType){ 
     return 1; 
    } 
    return o.score - this.score; 
} 
} 
+0

如果得分相同則它應該不會返回'0'? –

+0

沒有,如果一個商業類型的名稱得分與我需要它放置在商業之前的實際商業的名稱相同。 – maturecheese

+0

如果'o.score - this.score'溢出,您的解決方案仍然可能會中斷。 –

回答

2

考慮一下:

假設你有一個兩個對象bbt相同比分,一個是Business,另一個是BusinessType

compareTo(bt, b) -> -1 
compareTo(b, bt) -> 0 // Incorrect! This should be >= 0. 

另一個潛在的問題是o.score - this.score不考慮整數溢出。

也有可能您正在更改score和/或data的值,或者由於不正確的同步而導致值不一致。我建議您聲明兩個字段爲final。這將使該類不可變,並且也將消除對同步的需求(至少在這方面)。

(請參考其他的答案爲「合同」,你違反了的解釋。)

+0

我正在使用一個單線程執行器(我只是取消評分和排序,如果有一個新的密鑰輸入並重新開始),不能有任何同步問題。將使田野最終。 – maturecheese

+0

@maturecheese - 然而,如果你最後讓這些字段最終消除了這個問題是由變異引起的可能性。另外,請記住,其他人與您的問題類似(並閱讀本問答)*可能會在多線程環境中使用代碼。 *這個答案適合他們和你!* –

+0

好點,謝謝,並已更新 – maturecheese

0

Here是可比的文檔。它規定如下:

實現程序必須確保SGN(則x.compareTo(Y))== -sgn(y.compareTo(X))對於所有的x和y。 (這意味着則x.compareTo(Y)如果y.compareTo(X)拋出一個異常 必須拋出異常。)

實現類還必須確保關係是可傳遞: (則x.compareTo(Y) > 0 & & y.compareTo(z)> 0)意味着x.compareTo(z)> 0。

你的例子似乎並不滿足這些,因此,警告。

2

你違反,指出

SGN(比較(X,Y))== -sgn在comparator javadoc發現比較的合同(比較(Y,X))

實質上,你爲x和y的兩個實例返回-1,這樣if語句成立。這違反了契約合同。您應該嘗試返回0或拋出異常,如果它不應該發生。

相關問題