0

状況:

私はしばしばこの問題に遭遇し、それを解決する方法がわかりません。どこでどのように答えを探すべきかわかりませんが。だからここにあります。一部のオブジェクトを他のオブジェクトに保存する場合、それらを読み取り専用として、またはゲッターのみで保持できますが、これは同じです。このように、 MyInt の値を変更することはできません

public class ClassA {

    public readonly int MyInt;

    public string MyString;

}

これを次のようにコンテナに入れたい場合は問題ありません。

public class ClassB {

    public readonly ClassA MyClassA;

    public string MyString;

}

これは引き続き期待どおりに機能します。MyInt は読み取り専用で、MyStringA は読み取り専用ではありません。

問題:

しかし、MyClassA を取得して MyClassA.MyStringA を設定することはできます。「より厳密な」読み取り専用システムを使用する方法はありますか? 上記の例では、MyClassA の場合、MyClassA のフィールドをすべて読み取り専用にしたいと考えています。

私が考えることができる唯一の解決策は、別のクラス MyClassAreadonly を持つことです。しかし、それは醜く、便利ではないようです。

環境:

この動作を探している理由は、MyClassB.MyClassA.MyString を設定する前に、MyClassB.MyString にロジック (イベントの発生など) を追加してもらいたいからです。したがって、別の解決策は、 ClassB.MyClassA を非公開に設定して表示しないことです。しかし、MyClassA を取得できるのはうれしいことです。しかし、それを取得して変更すると、ClassB ロジックが欠落します。

PS: 私はそれを理解することはできませんが、十分に明確であることを願っています.

4

3 に答える 3

1

ClassAのプロパティを次のClassBようなプロパティにラップできます。

public class ClassB
{
    private readonly ClassA _myClassA = new ClassA();
    private string _myString;

    public string MyString 
    { 
        get
        {
            // your logic here
            return _myString;
        } 
        set 
        {
            // your logic here
            _myString = value;
        }
    }
    public string MyStringA { get { return _myClassA.MyString;}}
    public int MyIntA { get { return _myClassA.MyInt; }}
}
于 2012-06-20T07:20:29.910 に答える
0

「深い」不変性

@Damien_The_Unbeliever のコメントで述べたように、これ私の質問に対する完璧な「答え」です。C# には今のところ組み込みのソリューションがないため、回答を引用符で囲みます。

私の問題に対処するための最も近い代替手段は、この方法で使用したいオブジェクト (MyClassA) の不変ファサードを持つことです。

ありがとうダミアン。

この件に関する別の読み物: http://www.bluebytesoftware.com/blog/2007/11/11/ImmutableTypesForC.aspx

于 2012-06-20T07:56:03.217 に答える
0

追加のロジックを実装するために、ClassB が処理できるように ClassA にイベントを追加するのはどうですか?

public class ClassA
{
    public readonly int MyInt;

    private string _myString;

    public string MyString
    {
        get
        {
            return _myString;
        }
        set
        {
            _myString = value;
            if (MyStringChanged != null)
            {
                MyStringChanged(this, new EventArgs());
            }
        }
    }

    public event EventHandler MyStringChanged;
}


public class ClassB
{
    public readonly ClassA MyClassA;

    //It sounds like you wanted to use ClassB.MyString to manipulate ClassA.MyString, so you probably won't need this anymore?
    //public string MyString;

    public ClassB()
    {
        MyClassA = new ClassA();
        MyClassA.MyStringChanged += new EventHandler(MyClassA_MyStringChanged);
    }

    private void MyClassA_MyStringChanged(object sender, EventArgs e)
    {
        //Add your logic here
    }
}
于 2012-06-20T07:57:17.753 に答える