C# 从派生类设置只读对象

C# 从派生类设置只读对象,c#,.net,inheritance,readonly,readonly-collection,C#,.net,Inheritance,Readonly,Readonly Collection,我正在编写一个库,我们公司的其他开发人员将使用它。状态机基类具有允许状态的ReadOnlyCollection,等等。开发人员需要从该类继承并设置允许的状态 我想限制它们在其派生类的构造函数中初始化ReadOnlyCollection,以后不能修改它 如果我在基类中将ReadOnlyCollection声明为只读属性,那么这将不起作用,因为它不能在派生类的构造函数中修改 我认为这是一种并不罕见的情况。要实现这一点,任何优雅的方法都不能让开发人员重写只读集合?不要让他们自己初始化。使基类构造函数将

我正在编写一个库,我们公司的其他开发人员将使用它。状态机基类具有允许状态的
ReadOnlyCollection
,等等。开发人员需要从该类继承并设置允许的状态

我想限制它们在其派生类的构造函数中初始化
ReadOnlyCollection
,以后不能修改它

如果我在基类中将
ReadOnlyCollection
声明为只读属性,那么这将不起作用,因为它不能在派生类的构造函数中修改


我认为这是一种并不罕见的情况。要实现这一点,任何优雅的方法都不能让开发人员重写
只读集合

不要让他们自己初始化。使基类构造函数将集合作为参数:

public class BaseClass
{
      protected readonly Collection someObject;
      public BaseClass(Collection object)
      {
            someObject = object
      }
}
因此,当调用派生类构造函数时,它也应该使用集合对象调用基类构造函数 否则将是编译时错误。这将确保集合在构造函数中初始化,而不是在其他地方初始化

public class Derivedclass : BaseClass
{
      public DerivedClass() : base(/*pass the collection object here*/)
      {
      }
}

这仍然有一个缺陷,如果您获得集合的引用,您仍然可以通过调用派生类中集合的Add或remove方法来修改集合。唯一的问题是,如果它是只读的,您不能重新初始化。

它必须是只读集合吗? 我会选择数不清的

可以这样做,类似于srsyogesh的回答:

public abstract class StateMachine
{
    public StateMachine(params States[] allowedStates)
    {
        _allowedStates = allowedStates;
    }

    private readonly IEnumerable<States> _allowedStates;

    public IEnumerable<States> AllowedStates
    {
        get { return _allowedStates; }
    }
}

public class DerivedStateMachine : StateMachine
{
    public DerivedStateMachine()
        : base(States.State1, States.State2)
    {

    }
}
公共抽象类状态机
{
公共状态机(参数状态[]允许状态)
{
_allowedStates=allowedStates;
}
私有只读IEnumerable允许状态;
公共IEnumerable允许状态
{
获取{return\u allowedStates;}
}
}
公共类派生的StateMachine:StateMachine
{
公共派生的StateMachine()
:base(States.State1、States.State2)
{
}
}
当然,我们仍然可以将该属性转换回数组并对其进行更改,但这将是一种犯罪行为。取决于你的观众。为了更加防弹,您可以迭代内容,而不只是返回字段:

    public IEnumerable<States> AllowedStates
    {
        get
        {
            foreach(var state in _allowedStates)
                yield return state;
        }
    }
public IEnumerable允许状态
{
得到
{
foreach(允许状态下的var状态)
屈服返回状态;
}
}