Introduction : SOLID et Rust — une combinaison idéale
\nLes principes SOLID sont des règles fondamentales de la conception orientée objet qui aident à créer un code flexible, maintenable et évolutif. Bien que Rust ne soit pas un langage purement orienté objet (il utilise des traits et des structures au lieu de classes), les principes SOLID lui sont pleinement applicables. Dans cet article, nous analyserons chacun des cinq principes avec des exemples de code en Rust, en montrant comment ils aident à construire des systèmes fiables.
\nTout au long de l'article, vous verrez comment Rust, avec son système de possession, ses traits et ses génériques, rend l'implémentation de SOLID naturelle et puissante. Nous commencerons par le Single Responsibility et terminerons par le Dependency Inversion, en fournissant des exemples prêts à l'emploi.
\n\n1. Single Responsibility Principle (SRP) — principe de responsabilité unique
\nEssence : Chaque module, classe ou fonction ne doit avoir qu'une seule raison de changer. En Rust, cela signifie qu'une structure doit être responsable d'une seule tâche.
\n\nMauvais exemple (violation du SRP)
\nstruct Report {\n title: String,\n content: String,\n}\n\nimpl Report {\n fn generate(&self) -> String {\n format!("# {}\\n\\n{}", self.title, self.content)\n }\n\n fn save_to_file(&self, path: &str) -> std::io::Result<()> {\n std::fs::write(path, self.generate())?;\n Ok(())\n }\n\n fn send_email(&self, recipient: &str) {\n println!("Sending email to {} with report", recipient);\n }\n}\nIci, la structure Report est responsable de la génération, de la sauvegarde et de l'envoi — trois raisons différentes de changer. Cela viole le SRP.
Bon exemple (respect du SRP)
\nstruct Report {\n title: String,\n content: String,\n}\n\nimpl Report {\n fn generate(&self) -> String {\n format!("# {}\\n\\n{}", self.title, self.content)\n }\n}\n\nstruct ReportSaver;\n\nimpl ReportSaver {\n fn save(&self, report: &Report, path: &str) -> std::io::Result<()> {\n std::fs::write(path, report.generate())?;\n Ok(())\n }\n}\n\nstruct EmailSender;\n\nimpl EmailSender {\n fn send(&self, recipient: &str, message: &str) {\n println!("Sending email to {}: {}", recipient, message);\n }\n}\nMaintenant, chaque structure est responsable de sa propre tâche : Report pour les données et la génération, ReportSaver pour la sauvegarde, EmailSender pour l'envoi. Cela simplifie les tests et la maintenance.
2. Open-Closed Principle (OCP) — principe d'ouverture/fermeture
\nEssence : Les entités logicielles doivent être ouvertes à l'extension, mais fermées à la modification. En Rust, cela est réalisé via les traits et les génériques.
\n\nExemple : système de filtrage
\ntrait Filter<T> {\n fn apply(&self, items: &[T]) -> Vec<T>;\n}\n\nstruct EvenFilter;\n\nimpl Filter<i32> for EvenFilter {\n fn apply(&self, items: &[i32]) -> Vec<i32> {\n items.iter().filter(|&x| x % 2 == 0).copied().collect()\n }\n}\n\nstruct GreaterThanFilter {\n threshold: i32,\n}\n\nimpl Filter<i32> for GreaterThanFilter {\n fn apply(&self, items: &[i32]) -> Vec<i32> {\n items.iter().filter(|&&x| x > self.threshold).copied().collect()\n }\n}\n\nfn process<T: Clone, F: Filter<T>>(items: &[T], filter: F) -> Vec<T> {\n filter.apply(items)\n}\n\nfn main() {\n let numbers = vec![1, 2, 3, 4, 5, 6];\n let even = process(&numbers, EvenFilter);\n let greater = process(&numbers, GreaterThanFilter { threshold: 3 });\n println!("Even: {:?}, Greater: {:?}", even, greater);\n}\nNous pouvons ajouter de nouveaux filtres sans modifier le code existant de process. C'est une implémentation de l'OCP via le polymorphisme de traits.
3. Liskov Substitution Principle (LSP) — principe de substitution de Barbara Liskov
\nEssence :
Blogs
Book Recommendations
Lire aussi
IN() dans PDO : comment passer un tableau sans douleur ni erreurs
Travailler avec WebAssembly et Java : exécuter du code Java dans le navigateur
Revue de code en Java : quoi vérifier et comment donner un retour aux débutants
Pourquoi l'impression de "B" est-elle plus lente que "#" en Java ? Analyse avec exemples
API GraphQL avec Kotlin : tutoriel pratique étape par étape