2009-06-07 13 views
1

Je me demande quelle est la meilleure approche pour vérifier qu'une classe a tous les détails requis avant de pouvoir l'utiliser. Par exemple, disons que j'ai une classe Book et que je souhaite transmettre un ensemble de propriétés à propos du livre au constructeur Book.Comment vérifier une classe a toutes les propriétés configurées avant d'être utilisé?

Book book = new Book(bookProperties); 

Ce que je veux vous assurer que BookProperties est complète, à savoir a toutes les informations.

Disons que dans cet exemple, je donne les résultats suivants:

  • Titre du livre
  • Auteur
  • livre original Publishing Date de

Une façon est que je pourrais créer un constructeur par défaut qui accepte seulement les 3 items:

BookProperties bookProperties = new BookProperties("2001: A Space Odyssey", 
                "Arthur C. Clarke", 
                1968); 

Maintenant c'est ok, si nous avons seulement trois valeurs, mais disons que ma classe a 10 propriétés ou plus qui doivent être initialisées par l'utilisateur avant que la classe Book puisse être créée.

Une chose que je pensais était d'avoir une méthode dans le BookProperties appelé isValid. Puis dans le constructeur de la classe Book je verrais si bookProperties.isValid et j'affirmerais si le retour est faux.

Est-ce une bonne idée ou est-ce que je vais tout à fait faux?

Répondre

3

Si nécessite 10 valeurs, alors il n'est pas rare de passer 10 valeurs dans le constructeur - mais ce que vous décrivez ressemble plus à un objet entité. Pour plus de commodité, il est courant d'utiliser simplement les setters de propriété. Avec 3.0 C#, vous pouvez utiliser la syntaxe initialiseur pour ce faire facilement et clairement:

Book book = new Book { 
    Title = "2001: A Space Odyssey", 
    Author = "Arthur C. Clarke", 
    PublishedYear = 1968 
}; 

Vous pouvez utiliser un objet BookProperties (comme une sorte de constructeur) - mais dans ce cas, pourquoi ne pas faire la construction d'une méthode sur le constructeur? Ensuite, le constructeur fait la validation avant de créer un Book (vraisemblablement via un constructeur internal) - et déclenche une exception s'il y a un problème. Je suppose l'utilisation de BookProperties est (par exemple) pour permettre une Book immuable - mais il n'y a pas besoin pour le constructeur être immuable:

var bookProperties = new BookProperties(); // builder? 
bookProperties.Title = "2001: A Space Odyssey"; 
... 
Book book = bookProperties.CreateBook(); 

Personnellement, je viens d'utiliser l'approche Book (le plus haut ci-dessus) dans la plupart des cas - cette approche fonctionne bien avec les moteurs de sérialisation .NET et les frameworks de liaison communs (comme les constructeurs sans paramètres et les propriétés get/set), par exemple.Si vous voulez une validation, alors ajoutez simplement une méthode Validate() (ou la propriété IsValue {get;}) à Book. Ou mettre en œuvre IDataErrorInfo.

+0

Cependant, il peut être difficile de conserver des invariants de classe corrects à tout moment lorsque vous construisez une propriété d'état par propriété. Si vous ne faites pas attention, vous pouvez vous retrouver avec une classe qui a différents modes, selon si les propriétés ont été remplies ou non. Je préfère l'approche du générateur d'objet (BookProperties), mais en utilisant la syntaxe d'initialisation pour * it *, plutôt que la classe finale. –

+0

Les directives officielles sont que l'ordre des propriétés de réglage ne devrait pas importer; donc ** si ** vous êtes dans ce scénario, les setters de propriété ne sont pas une solution appropriée. Mais la plupart du temps ce n'est pas le cas ... –

+0

Je pense que je vais aller avec la méthode Validate() sur la classe des propriétés quand le constructeur du livre est appelé. Ensuite, il va erreur si le résultat est faux. –

1

Si ces propriétés sont vraiment essentielles, elles devraient être dans le constructeur. Vous pouvez bien sûr utiliser les surcharges pour omettre les propriétés qui ont une valeur par défaut acceptable.

10 ou même 20 paramètres peuvent ne pas être joli mais c'est mieux que les alternatives.

+0

C'était l'une des solutions auxquelles je pensais aussi. Mais je pensais que même 10 serait trop. –

Questions connexes