2015-09-10 18 views
0

我試圖解決以下幾點:我該如何讓lteq <=運算符與Scala中的元組一起工作?

val temp1 = (3, "hello") 
val temp2 = (2, "abcde") 
temp1 <= temp2 

返回錯誤

<console>:24: error: value <= is not a member of (Int, String) 
       temp1 <= temp2 
        ^

我試着加入以下到我的代碼:

implicit val tempOrdering = new Ordering[(Int, String)] { 
    override def compare(a: (Int, String), b: (Int, String)): Int = 
    { 
    if  (a._1 < b._1) { -1 } 
    else if (a._1 > b._1) { 1 } 
    else if (a._2 < b._2) { -1 } 
    else if (a._2 > b._2) { 1 } 
    else 0 
    } 
    override def lteq(a: (Int, String), b: (Int, String)): Boolean = compare(a, b) <= 0 
} 

implicit val tempPartialOrdering = new PartialOrdering[(Int, String)] { 
    override def tryCompare(a: (Int, String), b: (Int, String)): Option[Int] = { 
    if  (a._1 < b._1) { Some(-1) } 
    else if (a._1 > b._1) { Some(1) } 
    else if (a._2 < b._2) { Some(-1) } 
    else if (a._2 > b._2) { Some(1) } 
    else Some(0) 
    } 
    override def lteq(x: (Int, String), y: (Int, String)) = { 
    tryCompare(x, y).map(_ <= 0).getOrElse(false) 
    } 
} 

和temp1目錄< = temp2仍然不起作用。

我能夠運行諸如

List(temp1, temp2).min 

命令,但不

min(temp1, temp2) 

如此看來,Scala是不是看到我訂購的for(int,字符串)元組的聲明。

我可以用

tempPartialOrdering.lteq(temp1, temp2) 

引用我的聲明和一些我的同事的建議作出新的類只是(智力,字符串)元組,但我覺得這些解決方案不雅。我真的希望能夠使用普通的舊「< =」比較運算符!

有誰知道我在做什麼錯,那「< =」仍然不是(Int,String)的成員?有沒有辦法隱式設置它?

回答

4

試試這個:

scala> import Ordering.Implicits._ 
import Ordering.Implicits._ 

scala> (2,3) <= (1,2) 
res2: Boolean = false 
+0

這也適用於我的例子中的(Int,String)對 - 謝謝! –

+0

雖然您可能實際上需要混合解決方案,但如果這對中的第二個值是最重要的一個。我測試瞭如果我使用上面的隱式tempOrdering代碼並重寫,以便第一個值被首先評估,這就成立了。但是如果你不聲明順序,那麼默認值將是最重要的第一個值 –

0

你的同事是對的。創建一個自定義類型(aka類)。它比你所稱讚的要優雅得多。

0

我只想做到以下幾點。您可以根據需要擴展它以獲得額外的功能。它笨重,但它完成了工作,並允許您提出自定義排序。

implicit class stringIntTuple(a: (String, Int)) extends (String, Int)(a._1,a._2) { 
    def <= (x: (String, Int)): Boolean = { 
    this._2 <= x._2 
    } 
} 

temp1 <= temp2 
相關問題