.net 4.0 泛型接口的协变及抗变性的简单实例
.NET 4.0中一个新的特性是支持泛型接口的协变和抗变性。协变和抗变的概念来源于数学和物理学,在编程中的意义也不难理解。任何方法,它的参数类型都是协变的。比如你有方法ovid Method(Object o),你就可以在类的实例中这样调用Method("string"),String类型可以顺利的转换成Object类型并执行方法中的代码。 任何方法的返回类型都是抗变的。比如你有方法Object Method(),你就不能把这个方法的返回值赋给一个String对象:String s =Method();。泛型接口中的协变和抗变与这个概念类似。在读《C#高级编程》第七版中文版的时候发现翻译的有些问题,对这个特性的理解造成障碍,最后baidu了一下,找到了一遍不错的博文,理解了这个特性。(http://www.cnblogs.com/Ninputer/archive/2008/11/22/generic_covariant.html) 以下是我写的一个简单实例,帮助理解泛型接口的协变和抗变型。
using System;
namespace CovariantAndContravariant
{
/*
* We know String is inherit from Object.
* I use the ralation of this two class to show how Generic interface works.
*/
interface ICovariant<out T>
{
//支持协变的泛型接口在尖括号中用out声明。T在接口方法中只能作为返回类型。
T MethodCo();
}
interface IContravariant<in T>
{
//支持抗变的泛型接口在尖括号中用in声明。T在接口方法中只能作为参数类型。
void MethodContra(T param);
}
class ClassWithObject : ICovariant<Object>, IContravariant<Object>
{
public Object MethodCo()
{
Console.WriteLine("Have achieve the method: MethodCo in ClassWithObject.");
return new Object();
}
public void MethodContra(Object o)
{
Console.WriteLine("Have achieve the method: MethodContra in ClassWithObject.");
}
}
class ClassWithString : ICovariant<String>, IContravariant<String>
{
public String MethodCo()
{
Console.WriteLine("Have achieve the method: MethodCo in ClassWithString.");
return "";
}
public void MethodContra(String s)
{
Console.WriteLine("Have achieve the method: MethodContra in ClassWithString.");
}
}
class Program
{
static void Main(string[] args)
{
ICovariant<Object> myICovariantO = new ClassWithObject();
ICovariant<String> myICovariantS = new ClassWithString();
myICovariantO.MethodCo();
myICovariantO = myICovariantS; /* Can not compile this if you don't use 'out' in ICovariant. */
myICovariantO.MethodCo();
IContravariant<Object> myIContravariantO = new ClassWithObject();
IContravariant<String> myIContravariantS = new ClassWithString();
myIContravariantS.MethodContra("");
myIContravariantS = myIContravariantO; /* Can not compile this if you don't use 'in' in IContravariant. */
myIContravariantS.MethodContra("");
Console.ReadKey();
}
}
}
会得到以下输出:
Have achieve the method: MethodCo in ClassWithObject.
Have achieve the method: MethodCo in ClassWithString.
Have achieve the method: MethodContra in ClassWithString.
Have achieve the method: MethodContra in ClassWithObject.