虚拟成员的语法

时间:2011-01-23 19:47:48

标签: c# syntax

考虑以下用c#.net 4.0编写的类(通常在nhibernate类中找到):

public class CandidateEntity : EntityBase
{
    public virtual IList<GradeEntity> Grades { get; set; }

    public CandidateEntity()
    {
         Grades = new List<GradeEntity>(); 
    }
}

这一行得到了一个有根据的警告“构造函数中的虚拟成员调用”。 我应该在哪里初始化这个集合?

此致

4 个答案:

答案 0 :(得分:11)

支持领域是一种方式。另一种是使用私人二传手。这在nHibernate中很有效。

public virtual IList<GradeEntity> Grades { get; private set; }

public CandidateEntity()
{
     Grades = new List<GradeEntity>();
}

答案 1 :(得分:9)

使用支持字段并初始化构造函数中的支持字段。或者将课程密封。

private IList<GradeEntity> _grades

public virtual IList<GradeEntity> Grades
{
   get { return _grades; }
   set { _grades = value; }
}

public CandidatesEntity()
{
   _grades = new List<GradeEntity>();
}

答案 2 :(得分:0)

如果您创建类sealed,您也不会收到警告(因为如果您继承此类并覆盖该成员,则问题只是一个问题。)

OP评论后编辑:

啊,对。我通常只在处理继承的虚拟成员时遇到这种情况。 Yads的回答可能对你最有用。

请注意,您不必将整个属性设为虚拟。考虑一下:

List<Grade> Grades { 
     get { return _grades; }
     set { _grades = value; OnGradesChanged(); }

protected virtual OnGradesChanged()
{ }

通常,您不希望以不同的方式在派生类中存储Grades。您只需要在更改时进行更新。这样,您可以为派生类提供更多指导,并且您确信可以信任支持字段。

P.S。 您知道人们可以在没有课程的情况下编辑List<Grade>吗?您应该考虑使用ObservableCollection,其中包含在外部更改集合时的事件。在这种情况下,您只需要公开只读Grades属性。

答案 3 :(得分:-1)

创建一个名为 OnInit 的类似的overridable(虚拟)方法,并在其中初始化Grade,然后从构造函数中调用 OnInit

警告是通知您正在创建一个实施者难以覆盖的行为。