J'implémente un DelegateCommand
, et quand j'étais sur le point d'implémenter le ou les constructeurs, j'ai proposé les deux choix de conception suivants:
1: Avoir plusieurs constructeurs surchargés
public DelegateCommand(Action<T> execute) : this(execute, null) { }
public DelegateCommand(Action<T> execute, Func<T, bool> canExecute)
{
this.execute = execute;
this.canExecute = canExecute;
}
2: Avoir un seul constructeur avec un paramètre facultatif
public DelegateCommand(Action<T> execute, Func<T, bool> canExecute = null)
{
this.execute = execute;
this.canExecute = canExecute;
}
Je ne sais pas lequel utiliser parce que je ne sais pas quels avantages / inconvénients possibles viennent avec l'une des deux façons proposées. Les deux peuvent être appelés comme ceci:
var command = new DelegateCommand(this.myExecute);
var command2 = new DelegateCommand(this.myExecute, this.myCanExecute);
Quelqu'un peut-il m'orienter dans la bonne direction et donner des commentaires?
c#
class-design
parameters
constructors
Thomas Flinkow
la source
la source
Bitmap.FromFile
) sont également une optionRéponses:
Je préfère plusieurs constructeurs aux valeurs par défaut et personnellement, je n'aime pas votre exemple à deux constructeurs, il devrait être implémenté différemment.
La raison de l'utilisation de plusieurs constructeurs est que le principal peut simplement vérifier si tous les paramètres ne sont pas nuls et s'ils sont valides tandis que d'autres constructeurs peuvent fournir des valeurs par défaut pour le principal.
Dans vos exemples cependant, il n'y a pas de différence entre eux car même le constructeur secondaire passe a
null
comme valeur par défaut et le constructeur principal doit également connaître la valeur par défaut. Je pense que ça ne devrait pas.Cela signifie qu'il serait plus propre et mieux séparé s'il était implémenté de cette façon:
notez le
_ => true
passé au constructeur principal qui vérifie maintenant également tous les paramètresnull
et ne se soucie pas des défauts.Le point le plus important est cependant l'extensibilité. Plusieurs constructeurs sont plus sûrs lorsqu'il est possible que vous étendiez votre code à l'avenir. Si vous ajoutez plus de paramètres obligatoires et que ceux facultatifs doivent arriver à la fin, vous casserez toutes vos implémentations actuelles. Vous pouvez créer l'ancien constructeur
[Obsolete]
et informer les utilisateurs qu'il va être supprimé en leur donnant le temps de migrer vers la nouvelle implémentation sans casser instantanément leur code.D'un autre côté, rendre trop de paramètres facultatifs serait également source de confusion car si certains d'entre eux sont requis dans un scénario et facultatifs dans un autre, vous devrez étudier la documentation au lieu de simplement choisir le bon constructeur en regardant simplement ses paramètres.
la source
CultureInfo
objet. Je préférerais une API permettant auCultureInfo
paramètre d'être fourni via un paramètre supplémentaire, mais j'ai insisté sur le fait que s'il était fourni, il ne devrait pas l' êtrenull
. De cette façon, lesnull
valeurs accidentelles ne sont pas mal interprétées comme signifiant «aucune».Obsolete
l'ancien si vous voulez éviter de casser des choses, que vous ayez également des paramètres facultatifs ou non. Avec les paramètres facultatifs, vous ne devez le faire queObsolete
si vous en supprimez un.Étant donné que la seule chose que vous faites dans le constructeur est une affectation simple, la solution à constructeur unique peut être un meilleur choix dans votre cas. L'autre constructeur ne fournit aucune fonctionnalité supplémentaire et il ressort clairement de la conception du constructeur avec deux paramètres que le deuxième argument n'a pas besoin d'être fourni.
Plusieurs constructeurs ont un sens lorsque vous construisez un objet à partir de différents types. Dans ce cas, les constructeurs sont une substitution d'une fabrique externe car ils traitent les paramètres d'entrée et les mettent en forme pour une représentation de propriété interne correcte de la classe en cours de construction. Cela ne se produit cependant pas dans votre cas, c'est pourquoi un seul constructeur devrait être plus que suffisant.
la source
Je pense qu'il y a deux cas différents pour lesquels chaque approche peut briller.
Premièrement, lorsque nous avons des constructeurs simples (ce qui est généralement le cas, selon mon expérience), je considérerais les arguments facultatifs pour briller.
Buuuut, il y a des cas où les arguments optionnels dans les constructeurs rendent les choses clairement plus confuses. L'exemple évident est lorsque ces arguments facultatifs sont exclusifs (c'est-à-dire qu'ils ne peuvent pas être utilisés ensemble). Le fait d'avoir des constructeurs surchargés qui n'autorisent que les combinaisons d'arguments réellement valides garantirait l'application de la contrainte de temps de compilation de cette contrainte. Cela dit, vous devez également éviter de rencontrer ce cas (par exemple, avec plusieurs classes héritant d'une base, où chaque classe fait le comportement exclusif).
la source