当我们仍然可以在我们的抽象 class 中使用它们时,抽象属性的目的是什么?

What is the purpose of abstract properties, when we still can use them in our abstract class?

先来看例子:

using System;
using System.Windows.Forms;

namespace WindowsFormsApplication1
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            Person p = new Manager();
            Manager p2=new Manager();

            p.Name = "Ahmad";
            p.Introduce();
            p.SayHello();
            p2.SayHello();
            p2 = (Manager)p;
            p2.SayHello();
        }
    }

    public abstract class Person
    {
        protected Person()
        {
            Name = "Reza";
            Introduce();
        }

        public abstract string Name { get; set; }

        public void SayHello()
        {
            Name = "Ali";
            MessageBox.Show(Name);
        }
        public abstract void Introduce();
    }

    public class Manager : Person
    {
        public new void SayHello()
        {
            MessageBox.Show("Test2");
        }

        public override string Name { get; set; }

        public override void Introduce()
        {
            MessageBox.Show("Hello " + Name);
        }
    }
}

起初我没有为基 class 编写构造函数。

据我所知,抽象方法的目的是强制派生的class从中实现,因此我们无法实现抽象基础 class 中的方法。

然后我添加了一个摘要属性。我看到我们可以在基 class 中初始化 属性 并使用它。

1st: abstract 的目的不就是声明它们然后让 derived class 去实现它吗?
为什么我们可以在基class中使用属性?

我们可以一开始只实现一个非抽象的 属性,这没什么区别。

然后我添加了构造函数,事情变得更加复杂。我们可以在构造函数中使用 Introduce() 方法从 Child class 调用 Introduce() (我从调试器中了解到)。

所以这里Child继承自Father,但是我们在Child中调用了Father的一个方法,很奇怪,有点违反继承规则。

第二:我错过了什么?

编辑:

Wasn't the purpose of abstract to just declare them and let derived class to implement it? Why can we use the property in base class?

您不能使用 基class 中的抽象属性,因为您不能直接实例化它。您创建抽象 属性 的原因与您想要创建抽象方法的原因相同,即确保您的派生类型实现它。

您的 Name 属性 实际上并未使用 base-class 实例。当从 SayHello 调用时,它将转到 Name 派生类型 实现并使用它。

So Child inherits from Father here, but we call a method in Child from Father, which is strange and is somehow against the rules of inheritance. What have i missed?

这不仅奇怪,它是一个 错误 可能 导致 运行 次异常,因为事实上子对象尚未初始化。如果您要访问 Introduce 中通过管理器构造函数(而不是通过 字段初始化 )实例化的 Manager 的任何成员,您将得到一个异常:

public class Manager : Person
{
    public Manager()
    {
        s = "Hello";
    }

    private string s;

    public override string Name { get; set; }

    public override void Introduce()
    {
        Console.WriteLine(s.ToLower());
    }
}

当您现在调用 Introduce 时,您会看到 NullReferenceException,因为 s 尚未初始化。

如果要在派生类型上调用抽象方法,请确保在 对象实例化之后调用。也许通过基础上的 Initialize 方法。

您可以阅读Virtual member call in a constructor了解更多信息:

if you make a virtual method call in a constructor, and it is not the most derived type in its inheritance hierarchy, that it will be called on a class whose constructor has not been run, and therefore may not be in a suitable state to have that method called.