Introduction aux Design Patterns
Fait partie de la section Programmation Orientée Objet du Journey GO de Coddy. Leçon 85 sur 107.
Les design patterns sont des solutions réutilisables à des problèmes courants qui surviennent dans la conception logicielle. Ce ne sont pas du code que vous copiez directement, mais plutôt des modèles qui vous guident dans la manière de structurer vos types et leurs interactions pour résoudre des problèmes spécifiques.
Les patrons de conception sont généralement regroupés en trois catégories :
| Catégorie | Objectif | Exemples |
|---|---|---|
| Création | Mécanismes de création d’objets | Singleton, Factory, Builder |
| Structure | Composition de types en structures plus grandes | Adapter, Decorator, Composite |
| Comportement | Communication entre les objets | Observer, Strategy, Command |
En Go, les patrons de conception sont différents de ceux des langages POO traditionnels.
Sans classes ni héritage, Go met en œuvre des modèles à l’aide d’interfaces, de l’intégration de structures et de la composition. Par exemple, là où Java pourrait utiliser une classe abstraite, Go utilise une interface. Là où C++ pourrait utiliser l’héritage, Go utilise l’intégration.
Apprendre les patterns vous aide à reconnaître les problèmes courants et à communiquer efficacement les solutions avec les autres développeurs. Lorsque quelqu’un mentionne « utilisez le pattern Strategy ici », toute l’équipe comprend l’approche sans longues explications.
Au cours des prochaines leçons, vous implémenterez plusieurs modèles fondamentaux en Go, en commençant par des modèles de création comme Singleton et Factory, puis en passant à des modèles comportementaux comme Observer et Strategy.
Défi
FacileConstruisons un système simple de notifications qui montre comment les patrons de conception aident à organiser le code ! Tu vas créer une structure qui pourra facilement être étendue avec des patrons comme Observer ou Strategy dans les prochaines leçons, mais pour l'instant, concentre-toi sur la mise en place d'interfaces et de types propres qui suivent les bons principes de la POO.
Tu vas organiser ton code sur trois fichiers :
notifier.go: définir l'interface principale et les types de ton système de notifications.Crée une interface
Notifieravec une seule méthodeSend(message string) stringqui renvoie un message de confirmation.Implémente deux types de notificateurs concrets :
EmailNotifieravec un champAddress. Sa méthodeSendrenvoieEmail to [address]: [message]SMSNotifieravec un champPhoneNumber. Sa méthodeSendrenvoieSMS to [phone]: [message]
dispatcher.go: créer un répartiteur qui fonctionne avec n'importe quel notificateur grâce à l'interface.Construis une structure
NotificationDispatcherqui contient une tranche d'interfacesNotifier. Ajoute ces méthodes :AddNotifier(n Notifier)pour enregistrer un notificateurBroadcast(message string) []stringqui envoie le message à tous les notificateurs enregistrés et renvoie une tranche de toutes les chaînes de confirmation
Crée également un constructeur
NewNotificationDispatcher()qui renvoie un répartiteur initialisé.main.go: configurer les notificateurs et diffuser les messages.Lis le nombre de notificateurs à créer. Pour chaque notificateur, lis son type (
emailousms) et sa destination (adresse ou numéro de téléphone). Ajoute chacun d'eux à un répartiteur.Lis ensuite un message à diffuser. Envoie-le à tous les notificateurs et affiche chaque confirmation sur sa propre ligne.
Les entrées suivantes seront fournies :
- Ligne 1 : nombre de notificateurs
- Pour chaque notificateur : type (
emailousms), puis destination - Dernière ligne : message à diffuser
Par exemple, avec :
3
email
alice@example.com
sms
555-1234
email
bob@example.com
Server maintenance at midnightTa sortie doit être :
Email to alice@example.com: Server maintenance at midnight
SMS to 555-1234: Server maintenance at midnight
Email to bob@example.com: Server maintenance at midnightEt avec :
2
sms
555-9999
sms
555-0000
Meeting canceledTa sortie doit être :
SMS to 555-9999: Meeting canceled
SMS to 555-0000: Meeting canceledCette structure montre comment les interfaces permettent de créer des conceptions flexibles et extensibles. Le répartiteur ne connaît pas les types spécifiques de notificateurs. Il sait simplement qu'ils peuvent effectuer Send. C'est la base sur laquelle s'appuient des patrons comme Observer et Strategy !
Essayez vous-même
package main
import (
"bufio"
"fmt"
"os"
"strconv"
"strings"
)
func main() {
reader := bufio.NewReader(os.Stdin)
// Lire le nombre de notifiers
countStr, _ := reader.ReadString('\n')
count, _ := strconv.Atoi(strings.TrimSpace(countStr))
// Créer un nouveau dispatcher
dispatcher := NewNotificationDispatcher()
// Lire chaque notifier et l'ajouter au dispatcher
for i := 0; i < count; i++ {
notifierType, _ := reader.ReadString('\n')
notifierType = strings.TrimSpace(notifierType)
destination, _ := reader.ReadString('\n')
destination = strings.TrimSpace(destination)
// TODO: Créer le notifier approprié selon le type
// et l'ajouter au dispatcher
// Hint: Vérifier si notifierType est "email" ou "sms"
}
// Lire le message à diffuser
message, _ := reader.ReadString('\n')
message = strings.TrimSpace(message)
// TODO: Diffuser le message et afficher chaque confirmation
}
Cette leçon comprend un petit quiz. Commencez la leçon pour y répondre et suivre votre progression.
Toutes les leçons de Programmation Orientée Objet
1Fondamentaux de la POO en Go
Fichiers externesEspace de travail et modules GoPackages et importsNoms exportés et non exportésIntroduction à la POO en GoStructs comme classesDéfinir des méthodes sur des structsRécepteurs pointeurs ou par valeurInitialisation des structsFonctions constructeursRécapitulatif - Calculatrice simple4Interfaces
Introduction aux interfacesImplémentation impliciteL’interface comme contratInterface vide (any)Assertion de typeCommutation de typeComposition d’interfacesInterfaces Stringer et ErrorRécapitulatif - Calculateur de formes7Encapsulation
Champs exportés vs non exportésEncapsulation au niveau du packageMéthodes Getter et SetterDissimulation de l’information en GoRécapitulatif – Fiches d’étudiants10Génériques (Go 1.18+)
Introduction aux génériquesParamètres de typeContraintes de typeStructures génériquesSolution de contournement pour les méthodes génériquesRécapitulatif - Collection générique13Design Patterns – Partie 1
Introduction aux Design PatternsPattern SingletonPattern FactoryPattern Abstract FactoryPattern ObserverPattern Strategy2Plongée approfondie dans les types et les structs
Types de base et compositesDéfinitions de types personnalisésTags de structStructs anonymesStructs imbriquésValeurs zéro et valeurs par défautRécapitulatif - Carnet de contacts5La composition plutôt que l’héritage
Pourquoi Go n’a pas d’héritageBases de l’inclusion de structsPromotion des méthodesInclure plusieurs structsInclusion ou agrégationMasquage des méthodes inclusesRécapitulatif : hiérarchie des employés8Gestion des erreurs et POO
L’interface errorTypes d’erreurs personnalisésEnrobage des erreurs (fmt.Errorf)Erreurs sentinelleserrors.Is() et errors.As()Panic, Defer et RecoverRécapitulatif - Analyseur de fichiers11Bibliothèque standard et POO
io.Reader et io.Writersort.InterfaceInterface fmt.Stringerencoding/json avec des structsInterface http.HandlerRécapitulatif - Modèles d’API REST14Modèles de conception – Partie 2
Modèle CommandeModèle AdaptateurModèle DécorateurModèle Méthode modèleModèle ÉtatModèle CompositeMiddleware comme décorateur3Pointeurs et mémoire
Notions de base des pointeurs en GoPointeurs vers des structuresPassage par valeur ou par référenceLa fonction new()Garbage collection en GoRécapitulatif - Constructeur de listes chaînées6Polymorphisme en Go
Polymorphisme via les interfacesDuck typing en GoRègles de satisfaction des interfacesCollections polymorphesInjection de dépendancesRécapitulatif – Processeur de paiements9Concurrence et POO
Bases des GoroutinesCanaux et communicationCanaux tamponnés ou non tamponnésInstruction selectsync.Mutex et sync.RWMutexsync.WaitGroupConception de structures thread-safeRécapitulatif - Pool de workersEntraînez-vous par vous-même : Compilateur Go en ligne