2011-02-10 15 views
4

クラス でinitiazlingプロパティを使用しています。完全に初期化した後で検証メソッドを実行したいと思います。 明白な理由からコンストラクタを使用できません。何らかのクラスの初期化されたイベントでそれを行う方法はありますか?完全に初期化されたクラス

var t = new Foo 
       { 
       foo = ""; 
       } 

class Foo 
{ 
    public string foo {get; set;} 
    ... 
    public bool validate {get ; set;} 

    private void validation() 
    { 
    if(foo == "") 
     validate = false; 
    if ... 
    } 

} 
+0

私は思っていませんが、コンストラクタが呼び出されたと思います。 –

+0

コンストラクタでこれを行うことができないという明白な理由がわかりません。それを明確にすることはできますか? –

+0

私はそれがプロパティイニシャライザのためだと思う... – SWeko

答えて

0

あなたがプロパティに検証ロジックを追加することができます。プロパティが割り当てられた後にクラスが初期化されていることを確認し、初期化が完了したら静的イベントを発生させますイベント送信者をFooにキャストすることで、インスタンスへの参照を取得できます。

public string Foo 
{ get { return _foo; } 
    set 
    { 
    _foo = value; 
    if (IsInitialized) 
     OnClassInitialized(); 
    } 
} 

public static event EventHandler ClassInitialized; 

private OnClassInitialized() 
{ 
    if (ClassInitialized != null) 
     ClassInitialized(this, EventArgs.Empty); 
} 

使用法:

Foo.ClassInitialized += (sender, e) => 
{ 
    Foo foo = sender as Foo; 
    ... 
}; 
0

1つのアプローチは検証のために設計されたインターフェイスです。たとえばIValidationです。 IValidationは、Validateメソッドを含むことができます。振る舞いを提供する必要があるクラスは、管理可能な方法でこれを行うことができます。

これは、IMHOが悪い設計であるコンストラクタ内の膨張を防ぎます。

2

(注:わかりやすくするために、私はバーにプロパティの名前を変更し、簡単にFoo型と区別するために)

Barプロパティは、建設時に有効でなければならない場合は、なぜあなたはそれを必要とされていませんコンストラクタ?なぜあなたは無効なオブジェクトの構築を許可していますか?

class Foo 
{ 
    public Foo(string bar) { 
     if(!IsValidBar(bar)) 
      throw new ArgumentException("bar is not valid.", "bar"); 
     this.Bar = bar; 
    } 
    public string Bar {get; set;} 

    private bool IsValidBar(string bar) 
    { 
     // blah blah 
    } 
} 

また、あなたはBarプロパティの値なしFooのインスタンスを作成することができますが、あなたがセッターでこれを検証することができます無効な値にBarの設定を許可しない場合:

0

proprty初期化子の使用を避け、多くのプロパティがある場合はオプションのパラメータを使用して、そのコードをすべてコンストラクタに移動するだけです。そうすれば、あなたは一種のプロパティ初期化子コンストラクタを取得することができますが、初期化が完了した後でもクラスを検証することができます。このようなもの:

class Foo 
{  
    public string Foo {get; set;} 
    public string Bar {get; set;} 
    public bool IsValid {get ; set;} 

    private void Validation() 
    {  
     if(foo == "")   
     IsValid = false;  
    if ...  
    } 

    public void Foo(string foo = string.Empty, string bar = string.Empty) 
    { 
     Foo = foo; 
     Bar = bar; 
     Validation(); 
    } 
} 

..... 

var t = new Foo (Foo = "SomeString"); 

これは比較的新しいC#4構文です。

c#4を使用できない場合は、プロパティアクセサーを使用して検証を有効にすることができます。

しかし、これは各セットの妥当性を評価します。一度に多数のプロパティを設定すると時間がかかることがあります。あなたはまた、いくつかの遅延ロードと組み合わせでこのような何かをgetアクセサを使用することができます。

public bool IsValid 
{ 
    get 
    { 
    if (!isValidated) 
     Validation(); 
    return isValid; 
    } 
    private set { isValid = value; } 
} 

public string Foo 
{ 
    get { return foo; } 
    set 
    { 
    foo = value;   
    isValidated := false; 
    } 
} 
0

あなたはpostsharpのようなアスペクト指向プログラミングを使用することができます。 http://www.postsharp.org/。しかし、あなたはパフォーマンスを失う。

関連する問題