在 C# 代码中,如果 Rebar
类派生自 Reinforcement
类并且 RebarShape
类继承 ReinforcementShape
类。是否可以使用 RebarShape
类覆盖基类中的属性 ReinforcementShape
?
public class ReinforcementShape
{
}
public class RebarShape : ReinforcementShape
{
}
public class Reinforcement
{
public ReinforcementShape Shape { get; set; }
}
public class Rebar : Reinforement
{
// I want to override the Shape property
// but with its derived class which is RebarShape
// override the base property somehow!
public RebarShape Shape { get; set; }
}
更新:
当前的实现有什么问题?
在基地:
public virtual ReinforcementShape Shape { get; set; }
派生:
public new RebarShape Shape { get; set; }
最佳答案
您可以使用泛型来做到这一点,无需重写基类成员:
public class Reinforcement<T> where T: ReinforcementShape
{
public <T> Shape { get; set; }
}
public class Rebar : Reinforement<RebarShape>
{
}
现在您可以轻松创建 ReBar
的实例并访问其 Shape
- 属性,这是 RebarShape
的实例:
var r = new Rebar();
r.Shape = new RebarShape();
尝试将 ReinforcementShape
的实例分配给该属性将导致编译时错误,此时只有 RebarShape
有效。
编辑:根据您的编辑。您只能通过覆盖成员的实现来覆盖成员,而不是返回值。所以在你的情况下使用 virtual
不会做任何事情。然而,正如 R.Rusev 已经提到的,您只需要在派生成员上使用 new
关键字,这实际上会提供一个与您的基类同名的全新成员。但实际上它是一个完全不同的成员,与前者没有任何共同之处。但是,当您编写以下内容时
Reinforcement r = new Rebar();
// assign value to Shape
var shape = r.Shape;
使用的是原始实现,而不是您的新实现。所以 shape
将是 ReinforcementShape
类型而不是 RebarShape
。解决这个问题的唯一方法是首先将 r
声明为 Rebar
:
Rebar r = new Rebar();
// assign value to Shape
var shape = r.Shape;
但这会让您的应用程序的任何用户感到困惑,也许也会让您自己感到困惑。我通常不建议使用该关键字。最好使用第一种方法。
关于c# - 用派生类覆盖基类的属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42268826/