Quelle est la différence entre le modèle de conception Builder et le modèle de conception Factory?
Laquelle est la plus avantageuse et pourquoi?
Comment représenter mes résultats sous forme de graphique si je veux tester et comparer / contraster ces modèles?
Réponses:
Avec les modèles de conception, il n'y a généralement pas de solution "plus avantageuse" qui fonctionne pour tous les cas. Cela dépend de ce que vous devez mettre en œuvre.
De Wikipédia:
Entrée Wikipédia pour le modèle de conception d'usine: http://en.wikipedia.org/wiki/Factory_method_pattern
Entrée Wikipédia pour le modèle de conception de générateur: http://en.wikipedia.org/wiki/Builder_pattern
la source
Une fabrique est simplement une fonction wrapper autour d'un constructeur (éventuellement une dans une classe différente). La principale différence est qu'un modèle de méthode d'usine nécessite que l'objet entier soit construit en un seul appel de méthode, avec tous les paramètres transmis sur une seule ligne. L'objet final sera retourné.
Un modèle de générateur , d'autre part, est essentiellement un objet wrapper autour de tous les paramètres possibles que vous pourriez souhaiter passer dans une invocation de constructeur. Cela vous permet d'utiliser des méthodes de définition pour construire lentement votre liste de paramètres. Une méthode supplémentaire sur une classe de générateur est une méthode build (), qui passe simplement l'objet générateur dans le constructeur souhaité et renvoie le résultat.
Dans les langages statiques comme Java, cela devient plus important lorsque vous avez plus d'une poignée de paramètres (potentiellement facultatifs), car cela évite d'avoir à avoir des constructeurs télescopiques pour toutes les combinaisons possibles de paramètres. Un générateur vous permet également d'utiliser des méthodes de définition pour définir des champs en lecture seule ou privés qui ne peuvent pas être modifiés directement après l'appel du constructeur.
Exemple de base d'usine
Exemple de générateur de base
Il peut être utile de comparer les exemples de code de ces deux pages wikipedia:
http://en.wikipedia.org/wiki/Factory_method_pattern
http://en.wikipedia.org/wiki/Builder_pattern
la source
Le modèle Factory peut presque être considéré comme une version simplifiée du modèle Builder.
Dans le modèle Factory , l'usine est chargée de créer différents sous-types d'un objet en fonction des besoins.
L'utilisateur d'une méthode d'usine n'a pas besoin de connaître le sous-type exact de cet objet. Un exemple de méthode d'usine
createCar
peut renvoyer unFord
ou unHonda
objet typé.Dans le Builder modèle, les sous - types différents sont également créés par une méthode de constructeur, mais la composition des objets peuvent différer dans le même sous - classe.
Pour continuer l'exemple de voiture, vous pouvez avoir une
createCar
méthode de création qui crée unHonda
objet de type avec un moteur à 4 cylindres ou unHonda
objet de type avec 6 cylindres. Le modèle de générateur permet cette granularité plus fine.Des diagrammes du modèle Builder et du modèle de méthode Factory sont disponibles sur Wikipedia.
la source
Le modèle de conception de générateur décrit un objet qui sait créer un autre objet d'un type spécifique en plusieurs étapes. Il contient l'état requis pour l'élément cible à chaque étape intermédiaire. Pensez à ce que StringBuilder passe pour produire une chaîne finale.
Le modèle de conception d'usine décrit un objet qui sait créer plusieurs types d'objets différents mais liés en une seule étape, où le type spécifique est choisi en fonction de paramètres donnés. Pensez au système de sérialisation, où vous créez votre sérialiseur et il construit l'objet souhaité dans un seul appel de chargement.
la source
Construire un objet complexe étape par étape: modèle de générateur
Un objet simple est créé en utilisant une seule méthode: modèle de méthode d'usine
Création d'un objet à l'aide d'une méthode de fabrique multiple: modèle de fabrique abstrait
la source
Builder Pattern et Factory pattern, les deux semblent assez similaires aux yeux nus car ils créent tous les deux des objets pour vous.
Mais vous devez regarder de plus près
Cet exemple concret rendra la différence entre les deux plus claire.
Supposons que vous alliez dans un restaurant-minute et que vous commandiez de la nourriture .
1) Quelle nourriture?
Pizza
2) Quelles garnitures?
Capsicum, tomate, poulet BBQ, PAS D' ANANAS
Ainsi, différents types d'aliments sont fabriqués par le modèle Factory, mais les différentes variantes (saveurs) d'un aliment particulier sont fabriquées par le modèle Builder.
Pizza, Burger, Pâtes
Uniquement fromage, fromage + tomate + poivron, fromage + tomate, etc.
Exemple de code
Vous pouvez voir l'exemple d'implémentation de code des deux modèles ici
Builder Pattern
Factory Pattern
la source
Les deux sont des modèles de création, pour créer un objet.
1) Modèle d'usine - Supposons que vous ayez une super classe et N nombre de sous-classes. L'objet créé dépend du paramètre / de la valeur transmis.
2) Modèle Builder - pour créer un objet complexe.
la source
D'abord quelques choses générales pour suivre mon argumentation:
Le principal défi dans la conception de gros systèmes logiciels est qu'ils doivent être flexibles et simples à changer. Pour cette raison, il existe certaines métriques comme le couplage et la cohésion. Pour obtenir des systèmes qui peuvent être facilement modifiés ou étendus dans ses fonctionnalités sans avoir à repenser l'ensemble du système à partir de zéro, vous pouvez suivre les principes de conception (comme SOLID, etc.). Après un certain temps, certains développeurs ont reconnu que s'ils suivaient ces principes, il existe des solutions similaires qui fonctionnaient bien à des problèmes similaires. Ces solutions standard se sont avérées être les modèles de conception.
Les modèles de conception doivent donc vous aider à suivre les principes généraux de conception afin de réaliser des systèmes à couplage lâche avec une cohésion élevée.
Répondre à la question:
En demandant la différence entre deux modèles, vous devez vous demander quel modèle rend votre système plus flexible. Chaque modèle a son propre objectif d'organiser les dépendances entre les classes de votre système.
The Abstract Factory Pattern: GoF: "Fournir une interface pour créer des familles d'objets liés ou dépendants sans spécifier leurs classes concrètes."
Qu'est-ce que cela signifie: en fournissant une interface comme celle-ci, l'appel au constructeur de chacun des produits de la famille est encapsulé dans la classe d'usine. Et parce que c'est le seul endroit de votre système où ces constructeurs sont appelés, vous pouvez modifier votre système en implémentant une nouvelle classe d'usine. Si vous échangez la représentation de l'usine par une autre, vous pouvez échanger un ensemble complet de produits sans toucher à la majorité de votre code.
The Builder Pattern: GoF: "Séparez la construction d'un objet complexe de sa représentation afin que le même processus de construction puisse créer des représentations différentes."
Qu'est-ce que cela signifie: vous encapsulez le processus de construction dans une autre classe, appelée le directeur (GoF). Ce directeur contient l'algorithme de création de nouvelles instances du produit (par exemple, composer un produit complexe à partir d'autres parties). Pour créer les parties intégrales de l'ensemble du produit, le directeur utilise un constructeur. En échangeant le constructeur dans le directeur, vous pouvez utiliser le même algorithme pour créer le produit, mais modifier les représentations des pièces uniques (et donc la représentation du produit). Pour étendre ou modifier votre système dans la représentation du produit, il vous suffit d'implémenter une nouvelle classe de constructeur.
Donc, en bref: le but de Abstract Factory Pattern est d'échanger un ensemble de produits qui sont faits pour être utilisés ensemble. Le but du Builder Pattern est d'encapsuler l'algorithme abstrait de création d'un produit pour le réutiliser pour différentes représentations du produit.
À mon avis, vous ne pouvez pas dire que le modèle abstrait d'usine est le grand frère du modèle de constructeur. OUI, ce sont deux modèles de création, mais l'intention principale des modèles est entièrement différente.
la source
Une différence frappante entre Builder et Factory que je pouvais distinguer était la suivante
supposons que nous ayons une voiture
Dans l'interface ci-dessus, nous pouvons obtenir la voiture de la manière suivante:
mais si, une exception se produit lors de la création des sièges ??? VOUS N'OBTIENDREZ PAS DU TOUT L'OBJET // MAIS
supposons que vous ayez une implémentation comme celle-ci
Vous pouvez maintenant créer comme ça
Ici, dans le deuxième cas, même si une opération échoue, vous obtiendrez toujours la voiture.
Peut-être que la voiture ne fonctionne pas parfaitement plus tard, mais vous auriez l'objet.
Parce que la méthode d'usine vous donne la voiture en un seul appel, tandis que le constructeur construit un par un.
Bien que cela dépende des besoins du digne pour lequel aller.
la source
Modèle de constructeur télescopique
Analogie:
Courtoisie
la source
Builder et Abstract Factory sont destinés à des fins différentes. Selon le bon cas d'utilisation, vous devez sélectionner un modèle de conception approprié.
Builder principales caractéristiques:
Caractéristiques saillantes d' usine ( usine simple):
Souvent, les conceptions commencent par utiliser la méthode Factory (moins compliquée, plus personnalisable, les sous-classes prolifèrent) et évoluent vers Abstract Factory , Prototype ou Builder (plus flexible, plus complexe)
Jetez un œil aux articles connexes:
Garder le constructeur dans une classe distincte (interface fluide)
Modèles de conception: méthode Factory vs Factory vs Abstract Factory
Vous pouvez vous référer aux articles ci-dessous pour plus de détails:
fabrication de source
journaldev
la source
Usine : Utilisé pour créer une instance d'un objet où les dépendances de l'objet sont entièrement détenues par l'usine. Pour le motif d'usine abstrait , il existe souvent de nombreuses implémentations concrètes de la même usine abstraite. La bonne implémentation de l'usine est injectée via l'injection de dépendances.
Builder : utilisé pour construire des objets immuables , lorsque les dépendances de l'objet à instancier sont en partie connues à l'avance et en partie fournies par le client du constructeur.
la source
Les modèles Abstract Factory & Builder sont tous deux des modèles créatifs mais avec une intention différente.
Abstract Factory Pattern met l'accent sur la création d'objets pour les familles d'objets connexes où:
Le modèle de générateur se concentre sur la construction d'un objet complexe, étape par étape. Il dissocie la représentation du processus de construction de l'objet complexe, de sorte que le même processus de construction peut être utilisé pour différentes représentations.
la source
Une construction complexe est lorsque l'objet à construire est composé de différents autres objets qui sont représentés par des abstractions.
Considérez un menu dans McDonald's. Un menu contient une boisson, un plat principal et un accompagnement. Selon les descendants des abstractions individuelles qui sont composés ensemble, le menu créé a une autre représentation.
Là, nous avons obtenu deux instances du menu avec des représentations différentes. Le processus de construction à son tour reste le même. Vous créez un menu avec une boisson, un plat principal et un accompagnement.
En utilisant le modèle de générateur, vous séparez l'algorithme de création d'un objet complexe des différents composants utilisés pour le créer.
En termes de modèle de générateur, l'algorithme est encapsulé dans le directeur tandis que les générateurs sont utilisés pour créer les pièces intégrales. Faire varier le générateur utilisé dans l'algorithme du directeur entraîne une représentation différente car d'autres parties sont composées dans un menu. La façon dont un menu est créé reste la même.
la source
La principale différence entre eux est que le modèle Builder décrit principalement la création d'objets complexes étape par étape. Dans le modèle Abstract Factory, l'accent est mis sur les familles d'objets-produits . Le constructeur renvoie le produit à la dernière étape . Dans le modèle Abstract Factory, le produit est disponible immédiatement .
Exemple: disons que nous créons Maze
1. Usine abstraite:
2. Constructeur:
la source
Je pense que l'utilisation et la différence entre les modèles Factory & Builder peuvent être comprises / clarifiées plus facilement dans une certaine période de temps car vous avez travaillé sur la même base de code et en changeant les exigences.
D'après mon expérience, vous commencez généralement par un modèle Factory comprenant quelques méthodes de création statiques pour masquer principalement une logique d'initialisation relativement complexe. Au fur et à mesure que votre hiérarchie d'objets devient plus complexe (ou que vous ajoutez plus de types, de paramètres), vous finirez probablement par avoir vos méthodes remplies avec plus de paramètres et sans oublier que vous devrez recompiler votre module Factory. Tout cela augmente la complexité de vos méthodes de création, diminue la lisibilité et fragilise le module de création.
Ce point sera peut-être le point de transition / extension. Ce faisant, vous créez un module wrapper autour des paramètres de construction , puis vous pourrez représenter de nouveaux objets (similaires) en ajoutant plus d'abstractions (peut-être) et d'implémentations sans toucher à votre logique de création. Vous avez donc eu une logique «moins» complexe.
Franchement, faire référence à quelque chose de "faire créer un objet en une ou plusieurs étapes est la différence" car le seul facteur de diversité n'était pas suffisant pour que je puisse les distinguer car je pouvais utiliser les deux façons pour presque tous les cas auxquels je faisais face. maintenant sans aucun avantage. Voilà donc ce que j'en ai finalement pensé.
la source
Le principal avantage du modèle de générateur par rapport au modèle d'usine est dans le cas où vous souhaitez créer un objet standard avec de nombreuses personnalisations possibles, mais vous finissez généralement par en personnaliser quelques-unes.
Par exemple, si vous souhaitez écrire un client HTTP - vous allez configurer certains paramètres par défaut comme le délai d'écriture / lecture par défaut, les protocoles, le cache, DNS, les intercepteurs, etc.
La plupart des utilisateurs de votre client utiliseront simplement ces paramètres par défaut, tandis que d'autres utilisateurs voudront peut-être personnaliser certains des autres paramètres. Dans certains cas, vous souhaiterez simplement modifier les délais d'expiration et utiliser le reste tel quel, tandis que dans d'autres cas, vous devrez peut-être personnaliser par exemple le cache.
Voici les moyens possibles d'instancier votre client (extrait de OkHttpClient):
Si vous utilisez un modèle d'usine pour cela, vous finirez par écrire de nombreuses méthodes avec toutes les combinaisons possibles de paramètres de création. Avec le générateur, vous spécifiez simplement ceux qui vous intéressent et laissez le générateur le construire pour vous en prenant soin de tous ces autres paramètres.
la source
Le modèle de construction met l'accent sur la complexité de la création d'un objet (résolu par des «étapes»)
Le motif abstrait met l'accent «juste» sur «l'abstraction» d'objets (multiples mais liés).
la source
La différence est claire Dans le modèle de générateur, le générateur créera un type d'objet spécifique pour vous. Vous devez dire quel constructeur doit construire. Dans le modèle d'usine, en utilisant la classe abstraite, vous construisez directement l'objet spécifique.
Ici, la classe de générateur agit comme médiateur entre la classe principale et les classes de type spécifiques. Plus d'abstraction.
la source
Les deux sont très similaires, mais si vous avez un grand nombre de paramètres pour la création d'objets, certains d'entre eux étant facultatifs avec des valeurs par défaut, optez pour le modèle Builder.
la source
A mon humble avis
Builder est une sorte d'usine plus complexe.
Mais dans Builder, vous pouvez instancier des objets en utilisant d'autres usines , qui sont nécessaires pour construire un objet final et valide.
Donc, en parlant de l'évolution des "Patterns Créatifs" par complexité, vous pouvez y penser de cette façon:
la source
Les deux modèles viennent pour la même nécessité: cacher à un code client la logique de construction d'un objet complexe. Mais qu'est-ce qui rend un objet «complexe» (ou parfois compliqué)? C'est principalement dû à des dépendances, ou plutôt à l'état d'un objet composé d'états plus partiels. Vous pouvez injecter des dépendances par constructeur pour définir l'état initial de l'objet, mais un objet peut en nécessiter beaucoup, certains seront dans un état initial par défaut (simplement parce que nous aurions dû apprendre que définir une dépendance par défaut sur null n'est pas la manière la plus propre ) et un autre ensemble à un état déterminé par une condition. De plus, il existe des propriétés d'objet qui sont une sorte de "dépendances inconscientes", mais elles peuvent également prendre des états facultatifs.
il existe deux façons bien connues de dominer cette complexité:
Composition / agrégation: construisez un objet, construisez ses objets dépendants, puis connectez-les ensemble. Ici, un constructeur peut rendre transparent et flexible le processus qui détermine les règles qui conduisent à la construction du composant.
Polymorphisme: les règles de construction sont déclarées directement dans la définition de sous-type, vous avez donc un ensemble de règles pour chaque sous-type et une condition décide laquelle parmi ces règles s'applique pour construire l'objet. Une usine s'intègre parfaitement dans ce scénario.
Rien n'empêche de mélanger ces deux approches. Une famille de produits pourrait faire abstraction de la création d'objets effectuée avec un constructeur, un constructeur pourrait utiliser des usines pour déterminer quel objet composant instancier.
la source
À mon avis, le modèle Builder est utilisé lorsque vous souhaitez créer un objet à partir d'un tas d'autres objets et que la création d'une pièce doit être indépendante de l'objet que vous souhaitez créer. Il permet de masquer la création de pièce au client pour rendre le constructeur et le client indépendants. Il est utilisé pour la création d'objets complexes (objets qui peuvent être constitués de propriétés compliquées)
Alors que le modèle d'usine spécifie que vous souhaitez créer des objets d'une famille commune et que vous souhaitez qu'il soit cerated à la fois. Il est utilisé pour des objets plus simples.
la source
De: http://www.oodesign.com/builder-pattern.html
la source
Le modèle d'usine crée une implémentation concrète d'une classe au moment de l'exécution, c'est-à-dire que son intention principale est d'utiliser le polymorphisme pour permettre aux sous-classes de décider quelle classe instancier. Cela signifie qu'au moment de la compilation, nous ne connaissons pas la classe exacte qui sera créée, tandis que le modèle Builder est principalement concerné par la résolution du problème de l'antipattern des constructeurs télescopiques, qui se pose en raison du grand nombre de champs facultatifs d'une classe. Dans le modèle de générateur, il n'y a aucune notion de polymorphisme, car nous savons quel objet nous essayons de construire au moment de la compilation.
Le seul thème commun de ces deux modèles est le masquage des constructeurs et la création d'objets derrière les méthodes d'usine, et la méthode de construction, pour une construction d'objet améliorée.
la source
Le modèle d'usine vous permet de créer un objet à la fois tandis que le modèle de générateur vous permet d'interrompre le processus de création d'un objet. De cette façon, vous pouvez ajouter différentes fonctionnalités lors de la création d'un objet.
la source