gpt4 book ai didi

c# - 接口(interface)实现两次 "types may unify";为什么此解决方法有效?

转载 作者:IT王子 更新时间:2023-10-29 04:43:46 24 4
gpt4 key购买 nike

我在尝试为同一个类实现接口(interface)两次时遇到编译器错误,如下所示:

public class Mapper<T1, T2> : IMapper<T1, T2>, IMapper<T2, T1>
{
/* implementation for IMapper<T1, T2> here. */

/* implementation for IMapper<T2, T1> here. */
}

错误:

'Mapper' cannot implement both 'IMapper' and 'IMapper' because they may unify for some type parameter substitutions.

为什么这个解决方法有效?我想知道我是已经解决了问题还是只是欺骗了编译器。

public class Mapper<T1, T2> : MapperBase<T1, T2>, IMapper<T1, T2>
{
/* implementation for IMapper<T1, T2> here. */
}

public class MapperBase<T1, T2> : IMapper<T2, T1>
{
/* implementation for IMapper<T2, T1> here. */
}

编辑:我已将 MyClassMyClassBaseIMyInterface 更新为 MapperMapperBaseIMapper 来表示更真实的场景,在该场景中可能会出现此问题。

最佳答案

考虑这个实现:

public class MyClass<T1, T2> : IMyInterface<T1, T2>, IMyInterface<T2, T1>
{
/* implementation for IMyInterface<T1, T2> here. */

/* implementation for IMyInterface<T2, T1> here. */
}

什么是MyClass<int, int>实现?它实现了 IMyInterface<int, int>两次,因为 IMyInterface<T1, T2>IMyInterface<T2, T1>统一时 T1T2是平等的。这就是为什么同时实现 IMyInterface<T1, T2> 的原因和 IMyInterface<T2, T1>在同一个类(class)是不允许的。如果您尝试实现,例如 IMyInterface<int, T1>,同样的推理也适用。和 IMyInterface<T2, double> : 类型表达式统一为 T1 = double, T2 = int .

考虑这个实现:

public class MyClass<T1, T2> : MyClassBase<T1, T2>, IMyInterface<T1, T2>
{
/* implementation for IMyInterface<T1, T2> here. */
}

public class MyClassBase<T1, T2> : IMyInterface<T2, T1>
{
/* implementation for IMyInterface<T2, T1> here. */
}

您所做的是优先考虑 IMyInterface<T1, T2>IMyInterface<T2, T1> .如果T1T2是相等的,你有一个 MyClass<T1, T2> 的实例, IMyInterface<T1, T2>实现将被选中。如果你有一个 MyBaseClass<T1, T2> 的实例, IMyInterface<T2, T1>将选择实现。

这是一个向您展示行为的玩具程序。特别注意 a_as_i.M(0, 1) 的行为和 a_as_b.M(0, 1) .如果你要实现 I<T2, T1>明确在 B<T1, T2> (通过在方法名称前加上 I<T2, T1>. 前缀),将无法使用编译时语法调用它。反射(reflection)是必要的。

interface I<T1, T2>
{
void M(T1 x, T2 y);
}

class A<T1, T2> : B<T1, T2>, I<T1, T2>
{
public void M(T1 x, T2 y)
{
Console.WriteLine("A: M({0}, {1})", x, y);
}
}

class B<T1, T2> : I<T2, T1>
{
public void M(T2 x, T1 y)
{
Console.WriteLine("B: M({0}, {1})", x, y);
}
}

class Program
{
static void Main(string[] args)
{
//Outputs "A: M(0, 1)"
var a = new A<int, int>();
a.M(0, 1);

//Outputs "B: M(0, 1)"
var b = new B<int, int>();
b.M(0, 1);

//Outputs "A: M(0, 1)" because I<T1, T2>
//takes precedence over I<T2, T1>
var a_as_i = a as I<int, int>;
a_as_i.M(0, 1);

//Outputs "B: M(0, 1)" despite being called on an instance of A
var a_as_b = a as B<int, int>;
a_as_b.M(0, 1);

Console.ReadLine();
}
}

关于c# - 接口(interface)实现两次 "types may unify";为什么此解决方法有效?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22721763/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com