2011-07-04 41 views
8
def m(x: Int): Any = { } 
var set = new HashSet[Int => Any] 
set += m 
set += m 

set.size現在是2,並且set.contains(m)是錯誤的,因爲顯然m部分應用了兩次並創建了兩個函數對象。如果m是一個函數,它按預期工作。如果他們引用相同的方法,我想把它們當作平等對待。這可以做到嗎? (不轉向的地圖,去除鍵返回,或周圍其他的中間變量傳遞)如何把成套的方法呢?

回答

9

使用val fun = m _改造方法成功能添加之前。

做了set += m隱含地創建了一個新函數,它不等於執行set.contains(m)時創建的函數,例如,的m在功能方面都用途創建全新的並且因此不同的功能的對象。 (對不起,我剛纔看到,你已經說過了。)

這是正常的,如果你只需要拿到方法進入設置莫名其妙,然後使用一組對所有引用。所以下面的作品,以及:

def m(x: Int): Any = { } 
var set = new HashSet[Int => Any] 
set += m 
val fun = set.head // should not use head in real code but an iterator 
set.contains(fun) 

加成

或繞過其它中間變量

有作爲Scala中的一個方法對象沒有這樣的事情。因此,我不認爲這是不可能的,除非你比較他們的名字來比較兩種方法。 (可能使用反射,但我不確定這一點,這樣做也會非常糟糕 - 你不會有一組函數,而是方法引用,你需要將其轉換爲適當的方法然後再返回。)

1

你可以用該方法爲lambda具有相同簽名:

val m1 = (i:Int) => m(i) 
set += m1 
set += m1 
println(set.size) // Outputs "1" 
println(set contains m1) //Outputs "true"