11
votes

Devrais-je toujours coder à l'interface même si je ne vais jamais avoir une implémentation?

Je pense que le titre parle pour elle-même - pourquoi devrais-je écrire une interface, puis mettre en œuvre une classe concrète s'il n'ya jamais une implémentation concrète de cette interface?


0 commentaires

11 Réponses :


5
votes

La question est, s'il n'ya jamais d'être une implémentation concrète, il y a une interface?


2 commentaires

Correct, mais c'est une question, pas une réponse.


@Jason: Une bonne question est souvent la meilleure réponse (garçon a été tenté de l'écrire comme une question ;-))



36
votes

Je pense que vous ne devriez pas;)

Il n'est pas nécessaire d'ombrager toutes vos classes avec des interfaces correspondantes.

Même si vous allez faire plus de mise en œuvre plus tard, vous pouvez toujours extraire l'interface lorsqu'il devient nécessaire.


5 commentaires

+100 Si je pouvais, il est contre-productif de créer des interfaces inutilisées partout. Quand (si) vous en avez besoin, il est trivial de refroidir et d'extraire un.


D'accord. Une classe interne avec une seule implémentation n'a pas besoin d'une interface. L'interface peut être intéressante si elle fait partie d'une API externe - afin que les gens utilisant l'interface d'une manière que vous n'avez pas prédit ne soit pas obligé de prolonger votre implémentation ...


Que diriez-vous des tests? Je veux dire, EasyMock ne crée que des simulacres pour des interfaces.


Il y a une bibliothèque d'extension de classe EasyMock qui vous permet de se moquer de classes en béton easymock.org/downloads.html


@folone: ​​il n'a pas mentionné des tests;) Je suis d'accord que ce serait une bonne raison de créer une interface, mais il y a des situations où je viens de sous-classer la classe à moquer de la création d'une interface, bien que ce soit pourrait simplement être considéré comme la paresse :)



13
votes

C'est une question de granularité . Vous ne pouvez pas encombrer votre code avec des interfaces inutiles, mais elles sont utiles aux limites entre les couches.

Un jour, vous pouvez essayer de tester une classe qui dépend de cette interface. Ensuite, c'est bien que vous puissiez se moquer de cela.

Je suis constamment crée et supprimant des interfaces . Certains ne valaient pas l'effort et certains sont vraiment nécessaires. Mon intuition est principalement correcte mais Certaines refactorings sont nécessaires.


1 commentaires

Ces jours-ci, nous utilisons des moqueurs (ou des cadres de test similaires) pour se moquer des classes. Cette pratique consistait-elle à créer des interfaces pour les jours où vous deviez créer manuellement une classe de stub et injecter la dépendance dans votre test de l'unité (au lieu de simplement utiliser Mockito) pour se moquer de la dépendance? Cela fait beaucoup de sens pour moi si c'est le cas



0
votes

"seulement d'avoir une implémentation" == de célèbres derniers mots

Cela ne coûte pas beaucoup à faire une interface, puis de dériver une classe concrète de celle-ci. Le processus de fonctionnement peut vous faire repenser votre conception et conduit souvent à un meilleur produit final. Et une fois que vous l'avez fait, si vous avez déjà mangé ces mots - aussi souvent, vous n'aurez pas à vous en soucier. Vous êtes déjà défini. Alors que sinon, vous avez un tas de refactoring à faire et ça va être une douleur.

Editéd pour clarifier: Je travaille sur l'hypothèse que cette classe va être répandue relativement lointaine et large. Si c'est une minuscule classe utilitaire utilisée par une ou deux autres classes dans un seul paquet, alors oui, ne vous inquiétez pas pour cela. Si c'est une classe qui va être utilisée dans plusieurs packages par plusieurs autres classes, ma réponse précédente s'applique.


2 commentaires

Suite à vos conseils, vous aurez une énorme tas d'interfaces et d'usines inutiles, et cela sera une douleur. TRIPLING VOTRE CLASS Comptez uniquement pour des raisons de «programmation à une interface» vous coûtera chèrement en maintenance.


@Michael Borgwardt: Ouais, j'ai réalisé que je travaillais sur une hypothèse probomption de la classe éventuellement fausse. Les interfaces pour chaque petite classe est mauvaise. Mais les interfaces pour les plus importantes qui vont être réparties sont bonnes - même si vous pensez que vous n'ayez jamais une implémentation. Il est si facile de se révéler tort sur celui-là, ce n'est même pas drôle - et le refactoring n'est pas toujours facile.



1
votes

deux réponses quelque peu contradictoires à votre question:

  1. Vous n'avez pas besoin d'extraire une interface de chaque classe de béton que vous construisez et
  2. La plupart des programmeurs Java ne construisent pas autant d'interfaces que possible.

    La plupart des systèmes (même "Code jetable") évoluent et changent de loin ce que leur design original est destiné à eux. Les interfaces les aident à se développer de manière flexible en réduisant le couplage. En général, voici les signes d'avertissement que vous devriez coder à une interface:

    1. Vous soupçonnez-vous même qu'une autre classe de béton peut avoir besoin de la même interface (comme si vous soupçonnez que vos objets d'accès aux données pourraient avoir besoin de représentation XML sur la route - quelque chose que j'ai vécu)?
    2. Signez-vous que votre code peut avoir besoin de vivre de l'autre côté d'une couche de services Web?
    3. Votre code forme-t-il une couche de service à un client externe?

      Si vous pouvez rencontrer honnêtement "NON" à toutes ces questions, une interface pourrait être surchargée. Force. Mais encore une fois, les conséquences imprévues sont le nom du jeu dans la programmation.


0 commentaires

0
votes

La question devrait être la suivante: "Comment pouvez-vous être sûr que vous n'aurez jamais une implémentation concrète?"

Comment pouvez-vous être totalement sûr?

Au moment où vous pensiez cela, vous auriez déjà créé l'interface et vous auriez sur votre chemin sans hypothèses qui pourraient être fausses.

avec les outils de codage d'aujourd'hui (comme Resharper), cela ne prend vraiment pas beaucoup de temps pour créer et entretenir des interfaces aux côtés de vos cours, alors que vous découvrez maintenant que vous avez besoin d'une implémentation supplémentaire et de remplacer toutes les références de béton peuvent prendre une longue. temps et n'est pas amusant du tout - croyez-moi.


0 commentaires

1
votes

Vous devez décider de l'interface de programmation, en spécifiant les fonctions publiques. Si vous ne faites pas de bon travail, la classe serait difficile à utiliser.

Par conséquent, si vous décidez plus tard, vous devez créer une interface formelle, vous devez disposer du design prêt à partir.

Donc, vous devez concevoir une interface, mais vous n'avez pas besoin de l'écrire comme une interface, puis de la mettre en œuvre.


0 commentaires

0
votes

Beaucoup de ceci est tiré d'une conversation de Renfort sur Infoq: HTTP: // www.infoq.com/presentions/integration-TestSS-SMAM

Il y a 3 raisons d'avoir une classe:

  1. il contient une certaine valeur
  2. Il aide à persister une entité
  3. Il effectue un service

    La majorité des services devraient avoir des interfaces. Il crée une limite, masque la mise en œuvre et vous avez déjà un deuxième client; Tous les tests qui interagissent avec ce service.

    Fondamentalement si vous voudrez jamais se moquer de le moquer d'un test unitaire, il devrait avoir une interface.


0 commentaires

2
votes

Yagni - Vous n'aurez pas besoin de Wikipedia

Selon Pour ceux qui préconisent l'approche Yagni, la tentation d'écrire du code qui n'est pas nécessaire pour le moment, mais pourrait être à l'avenir, a les inconvénients suivants: P>

* The time spent is taken from adding, testing or improving necessary functionality.
* The new features must be debugged, documented, and supported.
* Any new feature imposes constraints on what can be done in the future, so an unnecessary feature now may prevent implementing a necessary feature later.
* Until the feature is actually needed, it is difficult to fully define what it should do and to test it. If the new feature is not properly defined and tested, it may not work right, even if it eventually is needed.
* It leads to code bloat; the software becomes larger and more complicated.
* Unless there are specifications and some kind of revision control, the feature may not be known to programmers who could make use of it.
* Adding the new feature may suggest other new features. If these new features are implemented as well, this may result in a snowball effect towards creeping featurism.


0 commentaires

1
votes

J'utilise une approche axée sur les tests pour créer mon code. Cela me conduira souvent à créer des interfaces dans lesquelles je souhaite fournir une mise en œuvre simulée ou factice dans le cadre de mon appareil de test.

Je ne créerais pas normalement aucun code à moins d'avoir une certaine pertinence pour mes tests et que vous ne pouvez pas facilement tester une interface, seule une implémentation, ce qui me conduit à créer des interfaces si j'en ai besoin lors de la fourniture de dépendances pour un boîtier de test.

Je créerai parfois des interfaces lors du refactoring, pour supprimer la duplication ou améliorer la lisibilité du code.

Vous pouvez toujours refroidir votre code pour introduire une interface si vous en découvrez que vous en avez besoin plus tard.

La seule exception à ce sujet serait si je conceviez une API pour la libération à une tierce partie - où le coût de la fabrication des changements d'API est élevé. Dans ce cas, je pourrais essayer de prédire le type de changements que je pourrais avoir à faire à l'avenir et de créer des moyens de créer mon API pour minimiser les futurs changements incompatibles.


0 commentaires

1
votes

Une chose que personne ne l'a mentionné encore, est-ce parfois nécessaire pour éviter les problèmes de dépendance. Vous pouvez avoir l'interface dans un projet commun avec peu de dépendances et la mise en œuvre dans un projet séparé avec beaucoup de dépendances.


0 commentaires