6

以下に示すように、コンストラクターで検証オブジェクトをインスタンス化しているため、set メソッドでユーザーの電子メールを検証できます。このアーキテクチャはベスト プラクティスですか、それとも欠陥がありますか? User クラスを Validation クラスに直接依存させないようにすることはできますか?

Class User {
  Private Email

//constructor
User() {
  Validation = new Validation
}

SetEmail(NewValue) {
  if (Validation.isEmail(NewValue)) {
    Email = NewValue
  }
}

関連する質問: set メソッドが無効な値を受け取った場合、適切な応答は何ですか? 2 つのオプションが表示されます

  1. 値を設定せずに false を返す
  2. とにかく値を設定しますが、オブジェクトのエラー プロパティを設定します。(したがって、 User.Error が設定されている場合、何か問題が発生したことがわかります)

オブジェクト プロパティの値が常に有効であることを保証できるので、#1 がベスト プラクティスだと思います。正しい?

4

2 に答える 2

10

これまでの提案はすべて、特に IOC と AOP のすべてに関して、やり過ぎのようです。

  1. Userクラスには電子メール アドレスが必要なので、クラスを作成し、クラスEmailAddressUserプロパティおよび/またはそのコンストラクタを介して電子メール アドレスを受け入れるようにします。EmailAddressその検証は、入力参照が nullかどうかと同じくらい簡単です。

  2. このEmailAddressクラスは単純ですが、一般に再利用可能な実装にすることができます (RFC ドキュメントに基づくことを検討してください)。不変である必要があり、無効な入力時にコンストラクターから例外をスローする必要があります。

  3. 電子メールアドレスは複合データ構造であるため、理想的には、クラスはクラス (RFC に基づく?) とクラス (RFC に基づく?)EmailAddressで構成される必要があります。繰り返しますが、これらの各クラスは不変のインスタンスを管理し、無効な入力による構築時に例外をスローする必要があります。EmailUserIdInternetDomain

「検証」は「モノ」ではなく、一般的な「アクション」のように思えます。したがって、クラスではなくメソッドであることに適しています。この場合、valid(input)Java や C# などの言語で、コンストラクターから呼び出されるプライベートな静的メソッド ( ) としてこれらの各クラスに検証を実装する傾向があります。多くの場合、その機能を質問の形式で公開すると便利です ( isValid(input))。

編集:

検証する必要があるすべての個別のデータ型には、独自のクラスが必要だと提案していますか?

これは、この問題に対処する確実な方法の 1 つであり、一般に値のタイプとして知られています (覚えてくれてありがとう、フランク)。その結果、いくつか (12 つか 2 つ) の明確に定義された再利用可能なクラス (おそらくEmailAddressPhoneNumberPersonNameなど) が作成されます。テストし、維持するのが難しい。

ソリューションを分割する方法は他にもありますが、私の提案には、成熟していて、よく理解されており、多くの堅実な設計原則と一致しているという利点があります。自分で発明する前に試してみることをお勧めします。

于 2008-12-08T05:46:26.837 に答える
1

私は...するだろう:

  1. 依存性注入を介して具体的な Validation オブジェクトへの結合を解除します。抽象 (純粋仮想) Validation クラスを定義し、具体的な検証クラスをそこから派生させ、抽象 Validation クラスへの参照を User クラスのコンストラクタ。

    C++ でこれを行う方法と理由についての優れた議論については、The C++ Reportの主題に関する Robert Martin の1996 年の記事を参照してください。

  2. false を返したり、何も言わずにプロパティを設定したりするのではなく、例外を発生させます。それが彼らの目的です。

于 2008-12-08T03:42:44.327 に答える