Scala 只有当要转换的函数至少有两个参数时,才能将函数隐式转换为二阶函数
我有一个隐式转换和高阶函数的问题。似乎只有当要转换的函数至少有两个参数时,函数到二阶函数的隐式转换才有效 作品:Scala 只有当要转换的函数至少有两个参数时,才能将函数隐式转换为二阶函数,scala,implicit-conversion,higher-order-functions,Scala,Implicit Conversion,Higher Order Functions,我有一个隐式转换和高阶函数的问题。似乎只有当要转换的函数至少有两个参数时,函数到二阶函数的隐式转换才有效 作品: implicit def conv(foo: Integer => String): String => String = null implicit def conv(foo: (Integer, Integer) => String): String => String => String = null 不起作用: implicit def co
implicit def conv(foo: Integer => String): String => String = null
implicit def conv(foo: (Integer, Integer) => String): String => String => String = null
不起作用:
implicit def conv(foo: Integer => String): String => String => String = null
作品:
implicit def conv(foo: Integer => String): String => String = null
implicit def conv(foo: (Integer, Integer) => String): String => String => String = null
故障点的完整示例:
{
implicit def conv(foo: Integer => String): String => String = null
def baadf00d(foo: Integer): String = null
def deadbeef(foo: String => String) = null
deadbeef(conv(baadf00d))
deadbeef(baadf00d)
}
{
implicit def conv(foo: Integer => String): String => String => String = null
def baadf00d(foo: Integer): String = null
def deadbeef(foo: String => String => String) = null
deadbeef(conv(baadf00d))
deadbeef(baadf00d) // <-------- DOES NOT COMPILE!
}
{
implicit def conv(foo: (Integer, Integer) => String): String => String => String = null
def baadf00d(foo: Integer, bar: Integer): String = null
def deadbeef(foo: String => String => String) = null
deadbeef(conv(baadf00d))
deadbeef(baadf00d)
}
{
隐式def conv(foo:Integer=>String):String=>String=null
def baadf00d(foo:Integer):字符串=null
def deadbeef(foo:String=>String)=null
死牛肉(conv(baadf00d))
死牛肉(baadf00d)
}
{
隐式def conv(foo:Integer=>String):String=>String=>String=null
def baadf00d(foo:Integer):字符串=null
def deadbeef(foo:String=>String=>String)=null
死牛肉(conv(baadf00d))
死牛肉(baadf00d)//String:String=>String=>String=null
def baadf00d(foo:Integer,bar:Integer):字符串=null
def deadbeef(foo:String=>String=>String)=null
死牛肉(conv(baadf00d))
死牛肉(baadf00d)
}
我错过了什么
谢谢
implicit def conv1(a: Function1[Int, String]): Function2[String, String, String] = null
def baadf00d1(i: Int): String = null
def deadbeef1(arg: Function2[String, String, String]) = null
deadbeef(baadf00d) // compiles
这是A=>B
和Function1[A,B]
之间没有发生的转换
在Predef
中还有一个函数
类型——请注意此处的类型差异:
scala> val f1: Function[Int, Int] = null
f1: Function[Int,Int] = null
scala> val f2: Function1[Int, Int] = null
f2: Int => Int = null
scala> :type f1
Function[Int,Int]
scala> :type f2
Int => Int
它是Function1
的别名,但具有不同的类型边界(如下面的注释所指出的)
这是因为函数定义不匹配。conv需要一个函数(Int,Int)=>String
,scala中的一个普通方法定义(未载波)变成了这个函数,就像baadf00d
是如何定义的一样
例如,函数:
def f(a: Int, b: Int): String
变成了一个
(Int, Int) => String
请注意,2个整数是元组!这与:
Int => Int => String
如果要将baadf00d重新定义为:
def baadf00d: Integer => Integer => String = _ => _ => ???
该代码不会编译,因为baadf00d现在“不同”,即使它正在做相同的事情
有关详细信息,请查看对象的定义:
Function1, Function2, Function3 ....
或者您甚至可以使用
val baadf00d2=baadf00d\uucode>将baadf00d
分配给val,然后它工作:type和:kind在REPL中统一对待它们,使其看起来更奇怪。from Predef.scala“type Function[-a,+B]=Function1[a,B]”你认为类型边界的差异会使它与上面例子中的implicit不匹配吗?Function1[A,B]
和A=>B
是同一件事(在类型上下文中)。在我看来,它就像Scala中的隐式解析。这是哪个Scala版本?好的,所以第二次转换不起作用的原因只是因为一个编译器错误,我猜…是的。在Scala中,baadf00d
和goodf00d
应分别转换为(Int)=>String
和Int=>String
。现在这些事情应该是一样的,但出于某种原因,隐式决断认为它们是不同的。您可以将baadf00d
传递到conv
中,这一事实证明它们是相同的,只是隐式解析太愚蠢了,无法理解它。