Scala的反射API是否提供了一种方法来判断一个Scala对象是否是一个函数?到目前为止,我能想到的最好的是:
import scala.reflect.runtime.universe._
def isFunction[T : TypeTag](x: T) =
weakTypeOf[T] <:< weakTypeOf[Function0[_]] ||
weakTypeOf[T] <:< weakTypeOf[Function1[_,_]] ||
weakTypeOf[T] <:< weakTypeOf[Function2[_,_,_]] ||
weakTypeOf[T] <:< weakTypeOf[Function3[_,_,_,_]] ||
weakTypeOf[T] <:< weakTypeOf[Function4[_,_,_,_,_]] ||
. . .
一定有更好的办法。
10:21 ~/Projects/210x/sandbox (2.10.x)$ scala
Welcome to Scala version 2.10.5-20140407-165700-ec05aeb3d6 (Java HotSpot(TM) 64-Bit Server VM, Java 1.7.0_40).
scala> import scala.reflect.runtime.universe._
import scala.reflect.runtime.universe._
scala> definitions.FunctionClass.contains(typeOf[Function1[_, _]].typeSymbol)
res1: Boolean = true
10:22 ~/Projects/211x/sandbox (2.11.x)$ scala
Welcome to Scala version 2.11.1-20140509-211642-d079e769b9 (Java HotSpot(TM) 64-Bit Server VM, Java 1.7.0_40).
scala> import scala.reflect.runtime.universe._
import scala.reflect.runtime.universe._
scala> definitions.FunctionClass.seq.contains(typeOf[Function1[_, _]].typeSymbol)
res0: Boolean = true
据我所知,公共API不允许您这样做,但始终可以访问内部:
scala> val st = scala.reflect.runtime.universe.asInstanceOf[scala.reflect.runtime.JavaUniverse]
st: scala.reflect.runtime.JavaUniverse = scala.reflect.runtime.JavaUniverse@db03ddc
scala> st.definitions.isFunctionType(st.typeOf[Int])
res0: Boolean = false
scala> st.definitions.isFunctionType(st.typeOf[Int => Int])
res1: Boolean = true
scala> st.definitions.isFunctionType(st.typeOf[Function0[Int]])
res2: Boolean = true
scala> st.definitions.isFunctionType(st.typeOf[Function0[_]])
res3: Boolean = true