Je comprends le rôle du modèle et de la vue dans le modèle Model-View-Controller, mais j'ai du mal à comprendre pourquoi un contrôleur est nécessaire.
Supposons que nous créons un programme d'échecs en utilisant une approche MVC; l'état du jeu doit être le modèle et l'interface graphique doit être la vue. Quel est exactement le contrôleur dans ce cas?
S'agit-il simplement d'une classe distincte qui a toutes les fonctions qui seront appelées lorsque, par exemple, vous cliquerez sur une tuile? Pourquoi ne pas simplement exécuter toute la logique du modèle dans la vue elle-même?
En utilisant votre exemple, le contrôleur serait ce qui déciderait ce qui était légal ou non. Le contrôleur ferait savoir à la vue comment organiser les pièces sur la carte au démarrage en utilisant les informations reçues du modèle. Il y a plus de choses qui peuvent être gérées par le contrôleur, mais la clé est de penser à Business Logic sur cette couche.
Il y a des moments où tout ce que le contrôleur fait est de transmettre des informations dans les deux sens, comme une page d'inscription. D'autres fois, le contrôleur est la partie difficile du développement, car il y a beaucoup de choses à faire au niveau de cette couche, comme appliquer des règles ou faire des calculs complexes par exemple. N'oubliez pas le contrôleur!
Pourquoi ne pas simplement exécuter toute la logique du modèle dans la vue elle-même?
Le contrôleur est la colle qui lie le modèle et la vue ensemble, et c'est également l'isolation qui les sépare. Le modèle ne devrait rien savoir de la vue et vice versa (du moins dans la version Apple de MVC). Le contrôleur agit comme un adaptateur bidirectionnel, traduisant les actions de l'utilisateur de la vue en messages vers le modèle et configurant la vue avec les données du modèle.
L'utilisation du contrôleur pour séparer le modèle et la vue rend votre code plus réutilisable, plus testable et plus flexible. Considérez votre exemple d'échecs. Le modèle inclurait bien sûr l'état du jeu, mais il pourrait également contenir la logique qui affecte les changements à l'état du jeu, comme déterminer si un coup est légal et décider quand le jeu est terminé. La vue affiche un échiquier et des pièces et envoie des messages quand une pièce bouge, mais elle ne sait rien de la signification derrière les pièces, comment chaque pièce se déplace, etc. Le contrôleur connaît à la fois le modèle et la vue ainsi que le flux global du programme. Lorsque l'utilisateur appuie sur le bouton `` nouveau jeu '', c'est un contrôleur qui indique au modèle de créer un jeu et utilise l'état du nouveau jeu pour configurer le plateau. Si l'utilisateur effectue un déplacement, le contrôleur relaie la commande au modèle et, en fonction de la réponse, autorise ou non le déplacement.
Regardez ce que vous obtenez en gardant le modèle et en affichant séparément:
Vous pouvez changer le modèle ou la vue sans changer l'autre. Vous devrez peut-être mettre à jour le contrôleur lorsque vous changez l'un ou l'autre, mais d'une certaine manière, cela fait partie de l'avantage: les parties du programme les plus susceptibles de changer sont concentrées dans le contrôleur.
Le modèle et la vue peuvent tous deux être réutilisés. Par exemple, vous pouvez utiliser la même vue de l'échiquier avec un flux RSS comme modèle pour illustrer des jeux célèbres. Vous pouvez également utiliser le même modèle et remplacer la vue par une interface Web.
Il est facile d'écrire des tests pour le modèle et la vue afin de s'assurer qu'ils fonctionnent comme ils le devraient.
Le modèle et la vue peuvent souvent tirer parti des pièces standard: tableaux, cartes, ensembles, chaînes et autres conteneurs de données pour le modèle; boutons, commandes, champs de texte, vues d'image, tableaux et autres pour la vue.
Il existe de nombreuses manières différentes de mettre en œuvre ce modèle de conception général, mais l'idée de base est de séparer les différentes préoccupations selon les besoins. MVC est une belle abstraction en ce sens que:
Modèle: Représente ces données, quoi que cela puisse signifier
Afficher: représente l'interface utilisateur, quoi que cela puisse signifier
Contrôleur: Représente la colle qui fait interagir ce modèle et cette vue, quoi que cela puisse signifier
Il est extrêmement flexible car il ne précise pas grand-chose. Beaucoup de gens gaspillent beaucoup de bande passante en discutant des détails de ce que chaque élément pourrait signifier, quels noms devraient être utilisés à la place de ceux-ci, et s'il devrait vraiment y avoir 3 ou 2 ou 4 ou 5 composants, mais cela manque le point certain degré.
L'idée est de séparer les différents "morceaux" de logique afin qu'ils ne se chevauchent pas. Gardez vos trucs de présentation ensemble, gardez vos trucs de données ensemble, gardez vos trucs de logique ensemble, gardez vos trucs de communication ensemble. Et ainsi de suite. Dans une certaine mesure, moins ces domaines de préoccupation se chevauchent, plus il est facile de faire des choses intéressantes avec eux.
C'est tout ce dont vous devriez vraiment vous inquiéter.
Jusqu'à présent, toutes les bonnes réponses. Je préfère penser que le contrôleur est principalement construit avec des questions comme quoi et où?
Ces petits extraits sont des exemples de la façon dont j'essaie de me souvenir de l'abstraction et du concept que MVC essaie de transmettre. Quoi, où et comment sont mes trois principaux processus de pensée.
Quoi et où => Contrôleur Comment et quand => Modèles et vues
Essentiellement, mes actions de contrôleur ont tendance à être petites et compactes et, à leur lecture, elles ont parfois l'air d'une perte de temps. En y regardant de plus près, ils agissent en tant que préposés aux feux de circulation, canalisant les diverses demandes vers les travailleurs compétents mais ne faisant aucun des travaux eux-mêmes.
Cela entre vraiment en jeu lorsque vous traitez avec des gestionnaires d'événements, mais vous avez toujours besoin du contrôleur pour gérer les interactions entre la vue et le modèle. Idéalement, vous ne voulez pas que la vue connaisse le modèle. Pensez-y, voulez-vous qu'un jsp effectue tous les appels de base de données directement? (À moins que ce soit quelque chose comme une recherche de connexion.) Vous voulez que la vue rende les données et n'ait pas de logique métier, à moins que ce soit la logique de rendu de vue, mais pas la logique métier perse.
Dans GWT, vous obtenez une séparation plus nette avec MVP. Il n'y a aucune logique métier (si c'est bien fait) dans la vue. Le présentateur agit comme un contrôleur et la vue n'a aucune connaissance du modèle. Les données du modèle sont simplement transmises à la vue.
Un contrôleur pourrait aider à résumer les interfaces de la vue et du modèle afin qu'ils n'aient pas à se connaître directement. Moins un objet doit en savoir, plus il devient portable et testable.
Par exemple, le modèle pourrait jouer une autre instance de lui-même via un contrôleur. Ou un contrôleur en réseau pourrait connecter les objets Vues de deux joueurs ensemble. Ou ce pourrait être un test de Turing où personne ne sait lequel.
La vue de document (c'est-à-dire la vue du modèle) est le modèle standard pour la majorité des applications Windows écrites en MFC, elle doit donc fonctionner dans de nombreux cas.
Je comprends le rôle du modèle et de la vue dans le modèle Model-View-Controller, mais j'ai du mal à comprendre pourquoi un contrôleur est nécessaire.
Êtes-vous sûr de cela? (Au moins comme décrit à l'origine) Le but du modèle est d'être le modèle de domaine. La vue est censée afficher le modèle de domaine à l'utilisateur. Le contrôleur est censé mapper l'entrée de bas niveau sur le modèle de haut niveau. Pour autant que je sache, le raisonnement va dans le sens de: A) une utilisation de haut niveau du SRP. B) Le modèle a été considéré comme la partie importante de l'application, évitez donc les changements sans importance et plus rapides. C) une logique métier facilement testable (et scriptable).
Pensez simplement si vous voulez rendre votre programme d'échecs utilisable par les aveugles, échangez la vue pour une version audible et un contrôleur qui fonctionne avec le clavier. Supposons que vous souhaitiez ajouter des jeux par courrier, ajoutez un contrôleur qui accepte le texte. Version nette du jeu? Un contrôleur qui accepte les commandes d'un socket ferait le travail. Ajoutez-y un joli rendu 3D, une nouvelle vue sympa. Zéro changement de modèle nécessaire Les échecs sont toujours des échecs.
Si vous mélangez l'entrée avec la représentation du modèle, vous perdez cette capacité. Soudain, les échecs ne sont pas des échecs, c'est des échecs avec une souris qui sont différents des échecs avec un clavier ou une connexion réseau.
Pensez à un navigateur qui affiche une page Web statique. Le modèle est le HTML. La vue est le résultat réel à l'écran.
Ajoutez maintenant du JavaScript. Voilà le contrôleur. Lorsque l'utilisateur clique sur un bouton ou fait glisser quelque chose, l'événement est envoyé au JavaScript, il décide de ce qu'il faut faire et modifie le code HTML sous-jacent (modèle) et le navigateur/moteur de rendu affiche ces modifications à l'écran (vue).
Peut-être qu'un autre bouton est cliqué, l'événement est envoyé à un gestionnaire (contrôleur) et cela peut entraîner l'envoi d'une demande de données supplémentaires à un service Web. Le résultat est ensuite ajouté au HTML (modèle).
Le contrôleur répond aux événements et contrôle ce qui est dans le modèle et donc ce qui est à l'écran/vue.
En prenant un peu de recul, vous pouvez considérer l'ensemble du navigateur comme la vue et le serveur comme le contrôleur et les données comme le modèle. Lorsque l'utilisateur clique sur un bouton du navigateur l'événement qu'il a envoyé au serveur (contrôleur), il rassemble les ressources sous forme de page HTML (modèle) et les renvoie au navigateur pour les afficher (Afficher)
Vers le bas sur le serveur, qu'il s'agisse d'asp, php ou Java le 'code' (Controller) reçoit l'événement click et interroge une base de données ou un référentiel de documents (modèle) et crée du HTML. À partir du serveur Du point de vue, le résultat de toutes ses actions est une vue (HTML) de sa banque de données sous-jacente (modèle). Mais du point de vue du client, le résultat de sa demande au serveur est son modèle (HTML)
Même si vous mélangez votre JavaScript dans votre HTML ou votre PHP dans votre HTML, le modèle, la vue, le contrôleur existent toujours. Même si vous pensez à votre demande à un serveur et à la réponse de la serveur comme une simple rue à double sens, il y a toujours un modèle, une vue et un contrôleur.
Je pense que MVC est stupide, peut-être que dans certains domaines, cela fonctionne bien, mais personnellement, même les sites Web que j'écris ne sont pas adaptés à la MVC. Il y a une raison pour laquelle vous entendez frontend, backend et jamais fin de base de données ou autre chose
IMO, il devrait y avoir une API (backend) et l'application qui utilise l'API (frontend). Je suppose que vous pourriez appeler la requête GET le contrôleur (qui appelle simplement le backend api) et le html la vue mais je n'entends généralement pas les gens parler de la vue comme du HTML pur ou du modèle étant une API de backend.
Tout OMI devrait être une API solide. En fait, ils n'ont pas besoin d'être solides (comme dans un environnement propre et bien construit), mais ses composants internes doivent rester privés et l'application/frontend/en dehors de l'API ne doit jamais avoir à dire la connexion à la base de données ni être capable de faire des requêtes brutes.
Maintenant, si votre code/conception implique de la colle, c'est bien. Si dans votre jeu d'échecs il y a un balisage que vous pouvez modifier pour habiller l'interface graphique, le GUI recueille les coordonnées/entrée et appelle MovePiece (srcPosition, dstPostion) (qui peut retourner un bool ou une énumération pour dire s'il s'agit d'un mouvement valide ou non ) et votre accord avec toute la logique étant dans le modèle, alors appelez-le bien MVC. Cependant, j'organiserais toujours les choses par classes et API et m'assurer qu'il n'y a pas de classe d'évier de cuisine qui touche tout (ni aucune API pour avoir à tout savoir).