J'ai cette interface: Cela fonctionne bien pour la plupart des utilisations. Mais lorsque j'essaie de modéliser une commande qui n'a que des effets secondaires (par exemple sans valeur de retour), je suis tenté d'écrire: p> est-ce un problème courant? Y a-t-il de meilleures pratiques pour modéliser les commandes J'ai essayé avec cet adaptateur, mais je pense que ce n'est pas optimal pour plusieurs Raisons: P> public abstract class VoidCommand implements Command<Void> {
@Override
public Void execute(String... args) {
execute2(args);
return null;
}
public abstract void execute2(String... args);
}
8 Réponses :
Gardez l'interface tel qu'il est: C'est pourquoi le void est dans la bibliothèque standard. Juste aussi longtemps que tout ce qui appelle la commande s'attend à ce que NULLS retienne.
et oui, NULL est la seule valeur que vous pouvez revenir pour annuler. P>
annulé code> comme types de retour, sauf si la réflexion est concernée. J'ai utilisé un modèle différent que je pense est plus explicite et strong> évite les nulls. C'est-à-dire que j'ai un type de réussite que j'appelle ok code> qui est renvoyé pour toutes les commandes telles que l'OP. Cela a très bien fonctionné pour mon équipe et a également propagé dans l'utilisation d'autres équipes. P> public enum Ok { OK; }
public class SideEffectCommand implements Command<Ok> {
@Override
public Ok execute(String... args) {
...
return Ok.OK; // I typically static import Ok.OK;
}
Je pense que la principale raison du vide est de représenter le type de méthodes de retour du vide (réflexion). Au moins retour à JDK 1.1 quand il a été inclus.
Oui, ça prédate les génériques. En effet, il est utilisé dans les génériques n'est qu'une convention, même si elle est évidente.
Qu'est-ce qui est intéressant dans votre exemple est l'utilisation de types paramétrés. Habituellement, vous auriez
interface Command<T> { public T execute(T someObject); }
que problème em> n'est pas que fort> commun, mais ni aussi rare ... je pense avoir vu une discussion à ce sujet il y a quelque temps, sur des appelables qui ne rentrent rien . p>
Je suis d'accord avec les autres affiches qu'il s'agit d'une bonne solution, beaucoup mieux que d'utiliser des objets ou un autre espace réservé factice. P>
Pouvez-vous relier la discussion s'il vous plaît?
Je tiens à utiliser Void code> explicitement. Il est facile de voir ce qui se passe sans autre classe impliquée. Ce serait bien si vous pouviez remplacer un
Void code> retour avec
void code> (et
integer code> avec
int code>, etc.) , mais ce n'est pas une priorité. P>
Lire les réponses que je dois dire que c'est le seul qui engage le problème au lieu de commenter la vie en général.
+1 pour cette réponse. Ne vous laissez pas accrocher sur le système de type de Java étant un peu maladroit avec l'interaction entre des types à base d'objets et primitifs.
Cet article ne traite pas de ce qui se passe lorsque le code s'attend à une déclaration sur une commande qui renvoie NULL.
Ce n'est pas un problème courant. Le problème que vous devez adresser est l'attente de votre interface. Vous combinez le comportement d'une interface d'effet non côté avec une interface qui permet aux effets secondaires.
considère ceci: p> il n'y a rien de mal à utiliser Lorsque nous passons autour des ensembles de données à l'aide des classes de collecte, mon équipe a accepté de Jamais fort> Retour NULL Même s'il est bien syntaxiquement. Le problème était que les classes qui utilisaient les valeurs de retour devraient constamment vérifier pour un voilé pour empêcher une NPE. En utilisant le code ci-dessus, vous le verriez partout: p> car il existe maintenant un moyen de savoir si la mise en œuvre a réellement un objet ou est null. Pour un cas particulier, assurez-vous que vous sachiez parce que vous connaissez votre mise en œuvre. Mais dès que vous commencez à les regrouper ou passez au-delà de votre horizon de codage (utilisé comme bibliothèque, maintenance future, etc.) Le problème NULL se présentera. P> Ensuite, j'ai essayé ceci: P>
public static void reportResults(String results){
ça me va bien. Comme les autres ont dit, Même mieux: Google, dans leur cadre GWT, utilisez la même idée dans leurs exemples pour un rappel retourné Void ( Exemple ici ). Je dis: Si Google le fait, il doit être au moins ok .. :) p> void code> était conçu à l'origine pour le mécanisme de réflexion, mais il est maintenant utilisé dans les génériques assez souvent pour décrire des situations telles que la vôtre. P>
Voici une implémentation de la meilleure des mondes multiples. Avec cette implémentation, les clients peuvent parler d'une commande sur la seule raison de ne pas utiliser code> si elles ne se soucient pas de la Valeur de retour et un
valuedCommand
Void code > tout droit est tout le
inesthip renvoyé null; code> les déclarations que vous serez forcées d'insérer. p> p>
Qu'en est-il de tous les "if (résultats! = Null) {}" Vous devez insérer dans les méthodes d'appel?
Si vous ne savez pas que votre commande renvoie void code>, vous ne devriez probablement pas tester le résultat pour
null code>, car vous n'auriez rien à voir avec elle à part Passez-le de toute façon.
La raison pour laquelle vous testez pour NULL est d'empêcher une nullpointerexception qui se produira »si vous ne savez pas que votre commande renvoie NUL». L'ignorant en ne mettant pas dans le si (résultats! = Null) {} garantit presque une NPE à l'avenir. C'est pourquoi vous ne mélangez pas les interfaces.
Et si au lieu d'avoir une interface comme: vous avez plutôt: p> alors les appelants feraient: P > public void doSomething(Command<?> cmd) {
cmd.execute(args);
if(cmd.hasResult()) {
// ... do something with cmd.getResult() ...
}
}
Cela a le problème malheureux de compléter les implémentations de commandement
Et aussi, il complique des choses pour l'appelant.
C'est parfaitement le fil-sûr aussi longtemps que la commande
GetResult a le problème même b> de mon exécuté: si t est vide, dois-je retourner null?
@DFA: Si t est annulé, lancez une exception. Les appelants ne doivent jamais appeler GetResult () sans vérifier HASRESULT () d'abord, tout code qui frappe ce cas est une erreur. Au moins, c'est comme ça que je le ferais, mais il apparaît que tout le monde dans ce fil n'est pas d'accord avec moi.
@Daniel Pryden: Je ne suis pas en désaccord avec vous. Le problème n'est pas comment pourriez-vous le coder, c'est ce que le code devrait s'attendre. Vérification du hasrsult () fonctionnerait mais il complique la relation entre la commande