4

ファウラー PoEAA p. 498 null-object パターンを次のように定義します (サンプルは短縮されています。言語は c# ですが、問題ありません)。

public class Customer
{
  public virtual string Name {get; set;}
}

public class NullCustomer : Customer, INull
{
  public override Name 
  {
     get { return "ImTheNull";}
     // setter ommitted
  }
}

INullマーカーインターフェイスとして使用されます。私は次の 3 つの理由から、このアプローチがあまり好きではありません。

  1. プロパティは仮想としてマークする必要があります
  2. エンティティ クラスを封印できなくなりました
  3. 少なくとも (n+1) 個の新しい型が導入されています (n 個の null オブジェクト、1 個のマーカー インターフェイス)

なぜこのように実装されていないのですか:

public class Customer
{
  public static readonly Customer NullCustomer = new Customer(){Name = "ImtTheNullCustomer";}

  public string Name {get; set;}
}

一般的に、Fowlers の例はすべてよく考えられていることがわかりましたが、ここで見落としているものがあることは明らかです。

4

4 に答える 4

10

継承の理由は、クラスの動作をオーバーライドすることです。あなたが考えている方法は、あなたが持っているオブジェクトがNullCustomer静的インスタンスと等しいかどうかを確認して決定を下そうとしているように思えますが、null オブジェクトのポイントは、リスコフの代入原則を支持することです。

つまり、null オブジェクトを使用して参照を設定すると、それに対する特別なチェックは行われず、単にそれを使用するだけで、別の動作を行う必要があります (実際には動作の欠如)。

于 2009-11-10T18:06:49.920 に答える
1

マジック値を使用した2番目の例の問題は、クラスにクラスの一部である他のアイテムがある場合、マジックに対してチェックを挿入して、情報またはその他の適切な情報を返すことを決定する必要があることです。

Null クラスを使用すると、クラスはそのようなチェックを必要とせずに最も意味のあるものを返します。

たとえば、顧客クラスは、必要に応じて DB に問い合わせた後、そのユーザーが費やした合計金額を返す場合があります。NullCustomer はreturn 0;. マジック値を使用すると、DB からダミー ユーザーの情報をフェッチするか、適切な処理を行う前に別の特定のチェックを実行する必要があります。

于 2009-11-10T18:06:16.567 に答える
0

私は C# プログラマーではありませんが、2 番目の例では次のようにできます。

Customer.NullCustomer.Name = "Not Null";

一般に、オブジェクトにはデータだけでなく動作があるため、より複雑になります。

于 2009-11-10T19:19:26.567 に答える
0

チャップが言ったことに追加します。Null Object パターンが使用されるため、受け入れ可能なデフォルトの値セットが存在します。さらに、MVC 内で NullCustomer を使用しようとした場合でも、存在しない可能性のあるデータを考慮する必要がなく、モデルを表すオブジェクトにアクセスできます。[ヌルのチェック]

于 2009-11-10T18:16:40.163 に答える