编程语言
首页 > 编程语言> > 在C#中允许覆盖扩展会出现什么问题

在C#中允许覆盖扩展会出现什么问题

作者:互联网

根据语言规范http://msdn.microsoft.com/en-us/library/bb383977.aspx

You can use extension methods to extend a class or interface, but not
to override them. An extension method with the same name and signature
as an interface or class method will never be called. At compile time,
extension methods always have lower priority than instance methods
defined in the type itself.

我不明白的是为什么会有这个限制?允许覆盖扩展会有什么编程问题?

一个简单的案例研究

基类Object具有方法ToString(),该方法默认将对象类型名称返回为字符串.可以争辩说,出于所有意图和目的,它旨在被覆盖.

默认情况下,Stream不提供ToString的替代,因为它不知道将字节转换为字符串是否有意义.

但是,作为解决方案的程序员,我知道如果将所有流转换为字符串,它们都是有意义的.但是,我不想或不能从流类派生.因此,我想扩展ToString方法以将流转换为字符串;像这样:

public static String ToString(this Stream stream)
{
    var memory = new MemoryStream(); //closable
    var reader = new StreamReader(memory);
    stream.Position = 0;
    stream.CopyTo(memory);
    memory.Position = 0;
    return reader.ReadToEnd();
}

但是,按照规范,这将永远不会在运行时调用.但是为什么在这种情况下限制如此严格?由于Stream是从Object派生的,这是否不意味着默认情况下,任何专门用于Stream的扩展方法都应覆盖基本类型的方法?

此外,在某些情况下,简单地将其命名为AsString不会有用.即WPF,它使用ToString作为后备来表示项目.

解决方法:

扩展方法在扩展对象的继承层次结构之外.

语言(和IDE)使该完全独立的类看起来像是扩展类型的一部分.

为了进行覆盖,需要更改整个继承模型和扩展机制-这是非常大的更改,可能是一个重大突破.

简而言之-这是一项功能,其实现成本将超过其用途.

标签:oop,extension-methods,c
来源: https://codeday.me/bug/20191031/1973712.html