从类构造函数中调用抽象方法

时间:2014-07-14 06:44:56

标签: c#

我有包含抽象方法的基类。

public abstract class ClassBase : IClassBase
{
    protected ClassBase()
    {
        ////   some code 
    }

    protected ClassBase(XmlNode settings)
          : this()
    {

    }

    protected abstract void Init(XmlNode settings);
}


public class Class_A : ClassBase
{
    public Class_A(XmlNode settings)
          : this(settings)
    {
        Init(settings);
    }

    protected override void Init(XmlNode settings)
    {


    }
}

从Class_A构造函数调用Init方法可以吗?

我尝试这样做并且运行正常 - 但是当构造函数运行时,虚拟表还没有准备好,据我所知,抽象方法还没准备好。

1 个答案:

答案 0 :(得分:6)

目前还不清楚完全您的意思是什么代码,因为您提供的代码由于几个原因而无法编译。最重要的是,您实际是否意味着从Init而不是ClassBase致电Class_A?如果没有,那么Init抽象似乎毫无意义。这个答案假定你 意味着。

  

从Class_A构造函数调用Init方法可以吗?

有效 - 但它通常不是一个好主意。

这不是"虚拟表"没有被创建 - 那很好,它将执行Class_A.Init。将立即将对象创建为其最终类型的实例。问题是,在 构造函数有机会执行之前,您在Class_A实例上调用了一个方法。这意味着它可能处于意外状态 - 例如,正常的前提条件可能不成立。

实施例

public class Class_A : ClassBase
{
    private readonly string text;

    public Class_A(XmlNode settings, string text)
        : base(settings) // Which calls Init(settings) as per intro paragraph
    { 
        if (text == null)
        {
            throw new ArgumentNullException("text");
        }
        this.text = text;           
    }

    protected override void Init(XmlNode settings)
    {
        // In here, text is still null... even though it can't be in any
        // other method.
    }
}

偶尔,它是最差的解决方案,但在这种情况下:

  • 确保没有更好的解决方案
  • 明确记录
  • 避免从其他任何地方调用该方法,因为编写适合于两者的实现通常很奇怪;我在初始化的一半时间#34;和"我已完全初始化"的状态。