【问题标题】:polymorphism for properties specified by interfaces由接口指定的属性的多态性
【发布时间】:2010-09-08 16:53:32
【问题描述】:
为什么这不起作用?
public class ClassOptions {}
public interface Inode {
ClassOptions Options {get;}
}
public class MyClass : Inode {
public ClassOptions Options { get; set; }
}
public class ClassDerivedOptions : ClassOptions {
}
public class MyDerivedClass : Inode {
public ClassDerivedOptions Options { get; set; } << does not implement INode...
}
[ 编译器消息告诉我为什么它会中断,但我想知道编译器为什么不让它通过的原因 - 如果有任何解决方法? - 谢谢]
【问题讨论】:
标签:
c#
c#-4.0
polymorphism
【解决方案1】:
它不起作用,因为 INode 接口显式调用 ClassOptions 类型的 Options 属性。 C# 不支持返回类型协方差(这是您在本例中所要求的)。
对于它的价值,Microsoft Connect 上还有一个专门针对返回类型协方差的语言功能请求:
Need covariant return types in C# / all .NET languages
如果您查看该页面,他们还提到常见的解决方法是使用显式接口实现:
public class MyDerivedClass : INode
{
public ClassDerivedOptions Options { get; set; }
public ClassOptions INode.Options { get { return Options; } }
}
【解决方案3】:
它不起作用,因为接口定义了合同,并且当您实现此合同时,方法签名必须完全匹配。一种可能的解决方法是使用通用接口:
public class ClassOptions
{ }
public class ClassDerivedOptions : ClassOptions
{ }
public interface INode<T> where T : ClassOptions
{
T Options { get; }
}
public class MyClass : INode<ClassOptions>
{
public ClassOptions Options { get; set; }
}
public class MyDerivedClass : INode<ClassDerivedOptions>
{
public ClassDerivedOptions Options { get; set; }
}
【解决方案4】:
处理这种情况的标准方法是显式实现接口:
public class MyDerivedClass : Inode {
// New, more specific version:
public ClassDerivedOptions Options { get; set; }
// Explicit implementation of old, less specific version:
ClassOptions Inode.Options
{
get { return Options; }
}
}
这就是大多数旧的IList 实现在泛型之前的工作方式,例如:指定更具体的T this[int index] 属性,然后显式实现object IList.this[int index],当set 被调用时抛出异常类型错误。
在您发布的示例代码中,您甚至需要明确的set,因为它不是Inode 接口的成员。