我有以下程序:
static void Main(string[] args)
{
CaptureFunction(MyFunction); // This line gets an error: "The call is ambiguous between the following methods or properties: CaptureFunction(System.Func<object,object>) and CaptureFunction(System.Func<int,int>)"
CaptureFunction(MyFunction2);
}
static void CaptureFunction(Func<object,object> myFunction)
{
myFunction.DynamicInvoke(3);
}
static void CaptureFunction(Func<int, int> myFunction)
{
myFunction.DynamicInvoke(3);
}
static object MyFunction(object a)
{
if (a is int)
return ((int) a)*3;
return 0;
}
static int MyFunction2(int a)
{
return a * 3;
}
我想弄清楚为什么我在那一行得到歧义错误。它们显然有两个不同的参数签名。我理解int
也可以被装箱成object
,但是,如果我传递实际的int
值,我将要求c#调用CaptureFunction(Func<int, int>)
方法,否则它应该调用其他CaptureFunction()
方法。有人可以解释这一点,请提供一个可能的工作围绕?
这是由于。net 4中引入的协方差/协方差。查看这里的信息。因为对不起,不是。net 4int
可以被转换为object
,编译器无法决定你指向哪个函数(因为Func可以被转换为Func)
以下编译:
static void Main(string[] args)
{
CaptureFunction((Func<object,object>)MyFunction); // This line gets an error: "The call is ambiguous between the following methods or properties: CaptureFunction(System.Func<object,object>) and CaptureFunction(System.Func<int,int>)"
CaptureFunction(MyFunction2);
}
static void CaptureFunction(Func<object,object> myFunction)
{
myFunction.DynamicInvoke(3);
}
static void CaptureFunction(Func<int,int> myFunction)
{
myFunction.DynamicInvoke(3);
}
static object MyFunction(object a)
{
if(a is int)
return ((int)a)*3;
return 0;
}
static int MyFunction2(int a)
{
return a * 3;
}
注意转换为Func<object,object>
如果你使用的是c# .net 4.0,请尝试使用动态
static void CaptureFunction(Func<dynamic, dynamic> myFunction)
{
myFunction.DynamicInvoke(3);
}
如果你没有使用4.0,那么就直接使用对象类型。
static void CaptureFunction(Func<object, object> myFunction)
{
myFunction.DynamicInvoke(3);
}
删除另一个类型为int的CaptureFunction的重载。
你正在传递一个委托给MyFunction…但是哪一个呢?可能是……都可以。
有超载的CaptureFunction将接受MyFunction签名。所以它无法知道你指的是哪个
似乎给定的函数满足两个委托签名。你可以通过显式声明函数来解决这个问题:
Func<int, int> intFunc = MyFunction2;
Func<object, object> objFunc = MyFunction;
CaptureFunction(intFunc);
CaptureFunction(objFunc);