Suffit-il que les méthodes se distinguent uniquement par le nom de l'argument (pas le type) ou vaut-il mieux le nommer plus explicitement?
Par exemple T Find<T>(int id)
vs T FindById<T>(int id)
.
Y a-t-il une bonne raison de le nommer plus explicitement (c'est-à-dire d'ajouter ById
) ou de ne garder que le nom de l'argument?
Une des raisons auxquelles je peux penser est lorsque les signatures des méthodes sont identiques mais que leur signification est différente.
FindByFirstName(string name)
et FindByLastName(string name)
T Find<T>(string name)
ou(int size)
comment envisagez-vous de résoudre les problèmes inévitables?ID
objet opaque et pas simplement unint
. De cette manière, vérifiez à la compilation que vous n'utilisez pas d'identifiant pour un int ou vice-versa dans une partie de votre code. Et avec ça vous pouvez avoirfind(int value)
etfind(ID id)
.Réponses:
Bien sûr, il y a une bonne raison de le nommer plus explicitement.
Ce n'est pas principalement la définition de la méthode qui devrait s'expliquer d'elle-même, mais l' utilisation de la méthode . Et tandis
findById(string id)
quefind(string id)
les deux se passent d'explication, il y a une énorme différence entrefindById("BOB")
etfind("BOB")
. Dans le premier cas, vous savez que le littéral aléatoire est en fait un identifiant. Dans ce dernier cas, vous n'êtes pas sûr - cela pourrait en fait être un prénom ou autre chose.la source
findById(id)
vsfind(id)
. Vous pouvez aller dans un sens ou dans l'autre.double Divide(int numerator, int denominator)
être utilisé dans une méthode:double murdersPerCapita = Divide(murderCount, citizenCount)
. Vous ne pouvez pas compter sur deux méthodes utilisant le même nom de variable car il existe de nombreux cas dans lesquels ce n'est pas le cas (ou lorsque c'est le cas, c'est une mauvaise désignation)Avantages de FindById () .
Avenir épreuvage : Si vous commencez avec
Find(int)
, et ont plus tard d'ajouter d' autres méthodes (FindByName(string)
,FindByLegacyId(int)
,FindByCustomerId(int)
,FindByOrderId(int)
, etc.), les gens comme moi ont tendance à passer des heures à la recherche pourFindById(int)
. Pas vraiment un problème si vous pouvez et va changerFind(int)
pourFindById(int)
une fois qu'il devient nécessaire - épreuvage avenir est au sujet de ces cas s.Plus facile à lire .
Find
est parfaitement bien si l'appel ressemble àrecord = Find(customerId);
YetFindById
est légèrement plus facile à lire si c'est le casrecord = FindById(AFunction());
.La cohérence . Vous pouvez systématiquement appliquer le motif
FindByX(int)
/FindByY(int)
partout, maisFind(int X)
/Find(int Y)
n'est pas possible car ils sont en conflit.Avantages de la recherche ()
Find
est simple et direct, etoperator[]
c’est l’un des 2 noms de fonction les plus attendus dans ce contexte. (Certaines alternatives populaires étantget
,lookup
oufetch
, selon le contexte).FindById(int id)
, nous pouvons facilement supprimer la redondance en la changeant enFind(int id)
, mais il y a un compromis - nous perdons un peu de clarté.Sinon, vous pouvez obtenir les avantages des deux en utilisant des identifiants fortement typés:
Implémentation de
Id<>
: Taper fortement les valeurs d'ID en C #Les commentaires ici, ainsi que dans le lien ci-dessus, ont soulevé de nombreuses préoccupations à propos
Id<Customer>
desquelles j'aimerais aborder:CustomerId
etOrderID
sont de types différents (customerId1 = customerId2;
=> bon,customerId1 = orderId1;
=> mauvais), mais leur implémentation est presque identique, nous pouvons donc les implémenter avec copier-coller ou avec métaprogrammation. Bien qu'il soit utile dans une discussion de révéler ou de cacher le générique, la métaprogrammation est ce à quoi servent les génériques.DoSomething(int customerId, int orderId, int productId)
. Les identifiants fortement typés préviennent également d’autres problèmes, y compris celui sur lequel l’OP a été interrogé.int aVariable
. Il est facile de savoir qu'un identifiant est retenuId<Customer> aVariable
et nous pouvons même dire qu'il s'agit d'un identifiant client.String
est juste une enveloppe autourbyte[]
. L'emballage ou l'encapsulation n'est pas en conflit avec le typage fort.operator==
etoperator!=
aussi, si vous ne voulez pas compter exclusivement surEquals
:.
la source
Une autre façon de penser à cela consiste à utiliser le type safety de la langue.
Vous pouvez implémenter une méthode telle que:
Où FirstName est un objet simple qui enveloppe une chaîne qui contient le prénom et signifie qu'il ne peut y avoir aucune confusion quant à ce que fait la méthode, ni dans les arguments avec lesquels elle est appelée.
la source
string name = "Smith"; findById(name);
qui est possible si vous utilisez des types généraux non descriptifs.DWORD
LPCSTR
clones, etc. et pensent que "c'est un int / string / etc.", il en arrive au point où vous passez plus de temps à entretenir vos outils qu'à concevoir du code. .int
s sont souvent sommés, multipliés, etc., ce qui n'a pas de sens pour les ID; donc je feraisID
distinct deint
. Cela peut simplifier une API, en limitant ce que nous pouvons faire avec une valeur (par exemple, si nous en avons unID
, cela ne fonctionnera qu'avecfind
, pas avecage
ou par exemplehighscore
). Inversement, si nous convertissons beaucoup, ou si nous écrivons la même fonction / méthode (par exemplefind
) pour plusieurs types, celaJe voterai pour une déclaration explicite comme FindByID .... Le logiciel devrait être construit pour le changement. Il devrait être ouvert et fermé (SOLID). La classe est donc ouverte pour ajouter une méthode de recherche similaire, comme par exemple FindByName, etc.
Mais FindByID est fermé et son implémentation est testée.
Je ne proposerai pas de méthodes avec prédicats, celles-ci sont bonnes au niveau générique. Et si basé sur le champ (ByID), vous avez une méthodologie complète différente.
la source
Je suis surpris que personne n'ait suggéré d'utiliser un prédicat tel que celui-ci:
Avec cette approche, vous réduisez non seulement la surface de votre API, mais vous donnez également plus de contrôle à l'utilisateur qui l'utilise.
Si cela ne suffit pas, vous pouvez toujours l'étendre à vos besoins.
la source