Senia的解決方案非常棒。不幸的是,他提到這不適用於Map
或String
。 這裏是另一種選擇(根據他的解決方案),這不:
import collection.generic.CanBuildFrom
import collection.breakOut
class Build[To]
def build[TargetSuperType] = new Build[TargetSuperType]
implicit def buildToCbf[From, T, TargetSuperType, To<:TargetSuperType](b: Build[TargetSuperType])
(implicit cbf: CanBuildFrom[Nothing,T,To]): CanBuildFrom[From,T,To] =
collection.breakOut
List(1, 2, 3).map{i => (i * 2, i/2.0, i.toString)}(build[Array[_]])
//res0: Array[(Int, Double, String)] = Array((2,0.5,1), (4,1.0,2), (6,1.5,3))
List(1, 2, 3).map{i => (i * 2, i.toString)}(build[Map[_,_]])
//res1: scala.collection.immutable.Map[Int,String] = Map(2 -> 1, 4 -> 2, 6 -> 3)
List('a', 'b', 'c').map(_.toUpper)(build[String])
//res2: String = ABC
這一點更詳細的,因爲現在你不只是做build[Array]
,但build[Array[_]]
。作爲交換,您可以指定所需的任何目標集合,而不考慮類型參數的數量(例如Map
和String
)。
另外,您還可以完全明確的(同樣使用breakOut
時)如果你選擇:
scala> List(1, 2, 3).map{i => (i * 2, i/2.0, i.toString)}(build[Array[(Int, Double, String)]])
res3: Array[(Int, Double, String)] = Array((2,0.5,1), (4,1.0,2), (6,1.5,3))
所有具有相同的語法(換句話說,使用相同的名稱build
,爲你的要求)
[這是](http://pastebin.com/rsmFtqdt)不是你想要的,但我想這是你能得到的最好的。這對'String'或'Map'不起作用。 – senia
是的,這是我想要的。我做了同樣的事情,但得到了混合的通用參數(在def中使用T,在代碼中使用A)並且無法從編譯器錯誤中找出它。 – IttayD
@senia也許答案是? –