Introduction et Modélisation avec UML

Kart yok

Le cours couvre les bases et les aspects avancés de l'UML, y compris les diagrammes, les méthodologies et les bonnes pratiques.

Introduction à la Modélisation Orientée Objet (MOO) avec UML

La modélisation orientée objet de systèmes logiciels est une approche essentielle en ingénierie logicielle. Ce document présente les concepts fondamentaux de la MOO et l'utilisation du langage UML (Unified Modeling Language) pour la conception et le développement de logiciels.

Problématique des logiciels

  • Les systèmes informatiques sont principalement composés de logiciels (80%) et de matériel (20%).
  • Le matériel est devenu relativement fiable et standardisé.
  • Les problèmes majeurs en informatique proviennent du logiciel, notamment des défis liés à sa qualité.

Taux de succès des projets logiciels (Standish Group, 1995) :

  • Succès : 16%
  • Problématique : 53% (non-respect du budget, des délais ou défauts de fonctionnalités)
  • Échec : 31% (projet abandonné)

Le taux de succès diminue avec la taille des projets et des entreprises.

Qualité du logiciel

Le Génie Logiciel vise à produire des logiciels de qualité, répondant à des critères spécifiques :

  • Utilité : Adéquation entre le logiciel et les besoins des utilisateurs.
  • Utilisabilité : Facilité d'utilisation.
  • Fiabilité : Capacité à fonctionner sans erreur.
  • Interopérabilité : Interactions avec d'autres logiciels.
  • Performance : Rapidité et efficacité.
  • Portabilité : Capacité à fonctionner sur différentes plateformes.
  • Réutilisabilité : Composants pouvant être réutilisés dans d'autres projets.
  • Facilité de maintenance : Malgré l'absence d'usure, la maintenance représente une part significative des efforts de développement.

Répartition des efforts et origine des erreurs

L'organisation Zeltovitz et De Marco a mené une étude qui a révélé des informations cruciales sur la répartition des efforts et des coûts liés aux erreurs dans le développement de logiciels :

Répartition effort dév. Origine des erreurs Coût de la maintenance
Définition des besoins 6% 56% 82%
Conception 5% 27% 13%
Codage 7% 7% 1%
Intégration Tests 15% 10% 4%
Maintenance 67%

La qualité du processus de fabrication garantit la qualité du produit.

Cycle de vie du logiciel

Pour obtenir un logiciel de qualité, il est impératif de maîtriser son processus d'élaboration. La vie d'un logiciel se compose de différentes étapes qui forment son cycle de vie, et dont la succession doit être contrôlée.

  1. Étude de faisabilité : Analyse de la viabilité du projet.
  2. Spécification : Définir les fonctionnalités du logiciel.
  3. Conception : Déterminer comment le logiciel fournira les fonctionnalités spécifiées.
  4. Codage : Implémentation du logiciel.
  5. Tests : Vérifier le bon fonctionnement du logiciel avec des données d'exemple.
  6. Maintenance : Corrections et évolutions post-déploiement.

Modélisation

Un modèle est une représentation abstraite de la réalité. Il simplifie un phénomène en omettant les détails non significatifs pour son comportement. Le concepteur choisit ce qui est important pour comprendre et prédire le phénomène.

Langages de modélisation

Un langage de modélisation doit définir :

  • La sémantique des concepts.
  • Une notation pour représenter ces concepts.
  • Des règles de construction et d'utilisation.

Types de langages de modélisation

  • Langages formels (Z, B, VDM) : Souvent mathématiques, ils offrent un grand pouvoir d'expression et permettent des preuves formelles sur les spécifications.
  • Langages semi-formels (MERISE, UML) : Souvent graphiques, ils sont plus faciles d'emploi, mais avec un pouvoir d'expression moindre.

L'industrie logicielle utilise divers langages adaptés à différents types de systèmes :

  • Systèmes procéduraux (MERISE).
  • Systèmes temps réel (ROOM, SADT).
  • Systèmes à objets (OMT, Booch, UML).

Les Ateliers Génie Logiciel (AGL) sont essentiels pour l'utilisabilité de ces langages.

Approches de conception

  • Approche descendante : Décomposer une fonction globale en fonctions simples à programmer. La fonction définit la forme du système.
  • Conception Orientée Objet (COO) : Basée sur les objets du système, plutôt que sur une décomposition fonctionnelle. La structure du système détermine sa forme. Permet une approche ascendante (partir des objets pour construire le système).

Introduction à UML

UML est un langage de modélisation unifié créé par James Rumbaugh, Ivar Jacobson et Grady Booch.

  • Objectifs :
    • Modéliser un système des concepts à l'exécutable, en utilisant les techniques orientées objet.
    • Réduire la complexité de la modélisation.
    • Être utilisable tant par les humains que par les machines (représentations graphiques traduisibles en code source, mais ne garantissant pas les mêmes propriétés mathématiques que les langages de spécification formelle).
  • Historique :
    • Né officiellement en 1994.
    • La version UML 2.0 (2005) a apporté des innovations majeures et étendu son champ d'application.

Modélisation Objet Élémentaire avec UML

UML propose différents diagrammes pour modéliser divers aspects d'un système.

Diagrammes de cas d'utilisation

Ces diagrammes modélisent le "QUOI" du système, c'est-à-dire l'inventaire et l'organisation des fonctionnalités attendues. Ils permettent de faire l'inventaire des fonctionnalités attendues et d'organiser les besoins pour identifier des relations (réutilisations potentielles).

Un cas d'utilisation est un service rendu à l'utilisateur, qui exprime une tâche de bout en bout avec un déclenchement, un déroulement et une fin propre à l'acteur qui l'initie.

Un acteur est toute entité externe qui interagit directement avec le système modélisé.

  • Un acteur correspond à un rôle, et non à une personne physique. Une même personne peut avoir plusieurs rôles (donc plusieurs acteurs), et plusieurs personnes peuvent jouer le même rôle (un seul acteur).
  • Les acteurs peuvent être :
    • Des utilisateurs du système (principaux).
    • Des périphériques (imprimantes).
    • Des logiciels existants.
    • Des systèmes informatiques externes.
  • L'acteur principal est à l'initiative des échanges pour réaliser un cas d'utilisation.
  • Les acteurs secondaires sont sollicités par le système.

Relations entre cas d'utilisation

  • Association : Lie un acteur à un cas d'utilisation, indiquant une interaction.
  • Inclusion (`<<include>>`) : Un cas d'utilisation A inclut un cas B, signifiant que B est une partie obligatoire de A.
  • Extension (`<<extend>>`) : Un cas B étend un cas A, où B est une partie optionnelle de A.
  • Généralisation : Un cas A est une généralisation d'un cas B (B est une sorte de A). La flèche pointe vers l'élément général. Cette relation se traduit par l'héritage en programmation orientée objet.
Les inclusions et les extensions sont représentées par des dépendances. Lorsqu'un cas B inclut un cas A, B dépend de A. Lorsqu'un cas B étend un cas A, B dépend aussi de A. On note toujours la dépendance par une flèche pointillée B --> A qui se lit « B dépend de A ». Lorsqu'un élément A dépend d'un élément B, toute modification de B sera susceptible d'avoir un impact sur A. Les « incude » et les « extend » sont des stéréotypes (entre guillements) des relations de dépendance.

Les relations entre cas d'utilisation favorisent la réutilisabilité (ex: un module d'authentification). Un cas trop complexe peut être décomposé en cas plus simples.

Documentation des cas d'utilisation

Les diagrammes de cas d'utilisation décrivent les grandes fonctions, mais ne détaillent pas le dialogue. Chaque cas d'utilisation doit être documenté pour éviter toute ambiguïté (nom, objectif, acteurs, étapes, pré/post-conditions, enchaînements alternatifs, contraintes non fonctionnelles).

Exemple de documentation pour le cas d'utilisation "Payer CB":

  • Identification:
    • Nom du cas : Payer CB
    • Objectif : Détailler les étapes pour un paiement par carte bancaire.
    • Acteurs : Client (principal), Banque (secondaire).
    • Date : 18/09
    • Responsables : Toto
    • Version : 1.0
  • Séquencements:
    • Le cas d'utilisation commence quand un client demande le paiement par CB.
    • Pré-conditions : Le client a validé sa commande.
    • Enchaînement nominal :
      1. Le client saisit les informations de sa carte bancaire.
      2. Le système vérifie la validité du numéro de CB.
      3. Le système vérifie la carte auprès du système bancaire.
      4. Le système demande le débit du client au système bancaire.
      5. Le système notifie le client du succès de la transaction.
    • Enchaînements alternatifs :
      1. Si le numéro est incorrect (étape 2), le client est averti et invité à recommencer.
      2. Si les informations sont erronées (étape 3), elles sont redemandées au client.
    • Post-conditions : La commande est validée, le compte de l'entreprise est crédité.
  • Rubriques optionnelles:
    • Contraintes non fonctionnelles : accès sécurisés (fiabilité), confidentialité des informations client.
    • Contraintes IHM : toujours demander la validation des opérations bancaires.

Diagrammes de classes

Les diagrammes de cas d'utilisation décrivent le QUOI, tandis que les diagrammes de classes spécifient la structure et les liens entre les objets composant le système. C'est le "QUI" du système.

Un objet est une instance d'une classe, la concrétisation d'un concept abstrait.

  • Exemple : "le stylo que vous utilisez" est une instance du concept "Stylo".

Une classe est la description d'un type d'objet, spécifiant ses caractéristiques : nom, attributs, opérations et relations.

  • Exemple : La classe "Vidéo" spécifie la manière de décrire tous les objets vidéo (désignation, label, auteur, etc.).
  • Des compartiments supplémentaires (responsabilités, exceptions) peuvent être ajoutés.
Attributs et Opérations

Les attributs et opérations sont les propriétés d'une classe, leur nom commence par une minuscule.

  • Un attribut décrit une donnée de la classe. Il peut avoir un type, une initialisation, et des modificateurs d'accès. Les attributs prennent des valeurs lors de l'instanciation de la classe.
    • Syntaxe : modifAcces nomAtt:nomClasse[multi]=valeurInit.
      • Exemple : # désignation : string, # prix : float = -1, # avisInternautes : Commentaire [0..*].
  • Une opération est un service offert par la classe (un traitement).
    • Syntaxe : modifAcces nomOperation(parametres):ClasseRetour.
      • Paramètres : nomClasse1 nomParam1, ..., nomClasseN nomParamN.
      • Exemple : + acheter(), + setPrix(value : float) : void.
  • Une opération est la spécification d'une méthode (sa signature) indépendamment de son implantation. UML 2 permet aussi de définir les opérations dans n'importe quel langage.
Relations entre classes
  • Héritage : Relation de généralisation/spécialisation permettant l'abstraction. Les éléments spécialisés héritent de la structure et du comportement des éléments plus généraux.
    • Exemple : Une classe "Livre" hérite d'une classe "Article" et a un prix et une opération acheter() sans besoin de les redéfinir.
    • Une classe enfant peut redéfinir des méthodes de la classe parent.
    • La surcharge d'opérations (même nom, signatures différentes) est possible.
    • Principe de substitution : Une instance d'une classe peut être utilisée partout où une instance de sa classe parent est attendue.
    • Une méthode abstraite est connue par son entête, mais sa réalisation est laissée aux classes enfants. Une classe est abstraite si elle contient au moins une méthode abstraite non réalisée.
    • L'héritage multiple (une classe avec plusieurs parents) est autorisé en C++, mais pas en Java.
  • Dépendance : Relation unidirectionnelle entre éléments du modèle (flèche ouverte pointillée `B --> A` se lit "B dépend de A"). Toute modification de A peut impacter B.
  • Association : Relation sémantique structurelle entre objets d'une classe, souvent utilisée pour représenter les liens possibles. Représentée par un trait entre classes.
    • La multiplicité contrôle le nombre d'objets impliqués dans une association (ex: 0..*, 1). Syntaxe : MultMin..MultMax.
    • La navigabilité spécifie le ou les sens de parcours de l'association à l'exécution, indiquée par une flèche. Une association navigable dans un seul sens peut être remplacée par un attribut.
    • Une association réflexive lie une classe à elle-même.
    • Une classe-association est une association raffinée avec ses propres attributs, lorsqu'ils n'appartiennent à aucune des classes liées.
    • Une association n-aire lie plus de deux classes. Représentée par un losange central et rarement utilisée.
  • Agrégation : Forme particulière d'association représentant une relation d'inclusion d'un élément dans un ensemble (le tout et ses parties). Représentée par un losange vide du côté de l'agrégat.
  • Composition : Décrit une contenance structurelle plus forte que l'agrégation (agrégation forte). Représentée par un losange plein. La destruction/copie de l'ensemble implique la destruction/copie de ses parties. Une partie n'appartient qu'à une seule instance composite.
Autres concepts
  • Encapsulation : Protéger le cœur du système des accès externes.
    • Les modificateurs d'accès définissent la visibilité :
      • + (public) : Visible partout.
      • # (protected) : Visible dans la classe et ses descendants.
      • - (private) : Visible uniquement dans la classe.
      • ~ (package) : Visible uniquement dans le paquetage.
  • Interfaces : Regroupent des opérations offrant un service cohérent. Définies comme des classes avec le stéréotype <<interface>>. Une relation de type réalisation relie l'interface à la classe qui l'implémente. Les classes clientes utilisent une relation de dépendance avec l'interface.
  • Attributs et associations dérivés : Sont calculés à partir d'autres éléments et symbolisés par un / devant leur nom.
  • Attributs et opérations de classe : Attributs ou opérations soulignées, partagées par toutes les instances (pour les attributs) ou propriétés de la classe et non des instances (pour les opérations).
  • Classes génériques : Classes paramétrables selon des valeurs ou types, définies avec un rectangle en pointillés et utilisées avec une dépendance stéréotypée <<bind>> (ex: généricité en Java, templates en C++).

Niveaux d'abstraction des diagrammes de classes

Les diagrammes de classes peuvent représenter un système à différents niveaux d'abstraction :

  • Spécification : Met l'accent sur les interfaces des classes.
  • Conceptuel : Capture les concepts du domaine sans se soucier de l'implémentation.
  • Implémentation : Détaille le contenu et l'implantation de chaque classe (le plus courant).

Démarche de construction d'un diagramme de classes

  1. Identifier les classes du domaine (concepts, substantifs).
  2. Trouver les associations entre classes (verbes).
  3. Identifier les attributs des classes (substantifs, adjectifs, valeurs).
  4. Organiser le modèle avec l'héritage.
  5. Tester les chemins d'accès.
  6. Itérer et affiner le modèle.

Diagrammes d'objets

Le diagramme d'objets représente les objets d'un système à un instant donné. Il illustre le modèle de classes, précise certains aspects et exprime des exceptions. Le diagramme de classes modélise des règles, le diagramme d'objets modélise des faits.

  • Les objets sont représentés par des cadres compartimentés, avec des noms soulignés. Les valeurs ou l'état d'un objet peuvent être spécifiés.
  • Les instances peuvent être anonymes, nommées, orphelines, multiples ou stéréotypées.
  • Un lien est une instance d'une association. Les multiplicités n'ont pas de sens au niveau des objets et ne sont donc pas représentées.
  • La relation de dépendance d'instanciation (`<<instantiate>>`) relie un classeur et ses instances, notamment les associations aux liens et les classes aux objets.

Diagrammes de séquences

Ces diagrammes décrivent le "COMMENT" les éléments du système interagissent entre eux et avec les acteurs, en ordonnant chronologiquement les messages.

Une ligne de vie représente un participant à une interaction (objet ou acteur).

  • Syntaxe : nomLigneDeVie[selecteur]:nomClasseOuActeur.
  • Un message définit une communication entre lignes de vie (envoi de signal, appel d'opération, création/destruction d'objet).
  • La réception d'un message provoque une période d'activité.
Types de messages
  • Synchrone : Bloque l'expéditeur jusqu'à la réponse du destinataire (appel de méthode). Le flot de contrôle passe de l'émetteur au récepteur. Un message de retour (pointillé) peut être associé.
    • Correspondent à des opérations dans le diagramme de classes.
  • Asynchrone : Non bloquant pour l'expéditeur (envoi de signal). Le message peut être pris en compte à tout moment ou ignoré.
    • Correspondent à des signaux dans le diagramme de classes (classes stéréotypées <<signal>>).
    • Le retour des messages asynchrones se fait par l'envoi de nouveaux messages asynchrones.
  • Création d'un objet : Flèche pointant sur le sommet d'une ligne de vie, ou message asynchrone "create".
  • Destruction d'un objet : Croix marquant la fin de la ligne de vie.
  • Message complet : Événements d'envoi et de réception connus. Représenté par une flèche.
  • Message perdu : Envoi connu, réception inconnue (broadcast).
  • Message trouvé : Réception connue, émission inconnue.
Syntaxe des messages
  • Messages : nomSignalOuOperation(parametres).
  • Arguments : nomParametre=valeurParametre (valeur fixe) ou nomParametre: valeurParametre (modifiable).
  • Messages de retour : attributCible=nomOperation(params):valeurRetour (en pointillés).
Fragments combinés

Permettent de décomposer une interaction complexe. Représentés par un rectangle avec un pentagone dans le coin supérieur gauche indiquant l'opérateur d'interaction (alt, opt, loop, par, ref, etc.).

  • Opérateurs de branchement : alternative, option, break, loop.
  • Opérateurs de parallélisme : parallel, critical region.
  • Opérateurs de contrôle de messages : ignore, consider, assertion, negative.
  • Opérateurs d'ordre de messages : weak sequencing, strict sequencing.
  • Une boucle (loop) : loop(minNbIterations, maxNbIterations).
  • L'opérateur par permet d'envoyer des messages en parallèle.
  • Le référencement (`<<ref>>`) permet de réutiliser une interaction existante. Chaque cas d'utilisation donne lieu à un diagramme de séquences.

UML et Méthodologie

Une méthodologie est un ensemble d'étapes ordonnées pour produire un système logiciel de qualité, dans des délais et coûts prévisibles. Elle produit des modèles, de la documentation et du code.

  • UML est un langage, pas une méthode (contrairement à MERISE).
  • Méthodes basées sur UML : RUP (Rational Unified Process), XP (eXtreme Programming).

Méthode minimale pour projets modestes

Objectif : Résoudre 80% des problèmes avec 20% d'UML.

  1. Définir les besoins :
    • Identifier les limites du système et les acteurs.
    • Identifier les cas d'utilisation, les structurer en packages, ajouter les relations et les classer par importance (priorité, risque).
  2. Modèle du domaine :
    • Décrit les concepts invariants du domaine d'application (classes sans opérations).
    • Étapes : identifier les concepts, ajouter associations et attributs, généraliser, structurer en packages.
  3. Séquences système :
    • Formalisent les cas d'utilisation textuels en diagrammes de séquences.
    • Le système est une "boîte noire" (ligne de vie "Système").
    • Les opérations système sont les messages des acteurs vers le système.
  4. Diagramme des Classes Participantes (DCP) :
    • Décrit les classes d'analyse :
      • Classes métier (ou entités) : Objets métier, correspondent au modèle du domaine.
      • Classes de dialogue : Interactions entre acteurs et application.
      • Classes de contrôle : Abstraient les fonctionnalités, lient dialogue et métier, contrôlent la cinématique.
    • Le DCP enrichit le modèle du domaine avec les classes d'interaction et de contrôle.
    • Architecture en couches : les dialogues se lient aux contrôles ou autres dialogues ; les classes métier aux contrôles ou autres classes métier ; les contrôles à tous types de classes.
  5. Diagrammes d'interaction :
    • Éclatent la ligne de vie "Système" des DSS pour détailler les classes d'analyse.
    • Définissent les opérations nécessaires des classes métier et de contrôle (messages synchrones).

Rational Unified Process (RUP)

Une méthodologie de développement itérative et incrémentale, pilotée par les cas d’utilisation et centrée sur l’architecture.

  • RUP est une approche itérative qui vise à minimiser les risques en produisant des incréments successifs du logiciel.
  • Chaque itération inclut spécification, conception, implémentation et tests.
Principes
  • Piloté par les cas d'utilisation : Focalisé sur l'utilité du logiciel pour les utilisateurs.
  • Centré sur l'architecture : Modélisation de différentes perspectives (vues de Krutchen : cas d'utilisation, logique, composants, déploiement, implémentation).
  • Itératif et incrémental : Le développement est un processus graduel d'élimination des risques, chaque itération produisant une nouvelle version exécutable.
Phases du développement RUP
  1. Initialisation :
    • Définition du cadre du projet, inventaire du contenu et élaboration des cas d'utilisation critiques.
    • Produit un document de vision, un modèle de cas d'utilisation préliminaire, un glossaire, une analyse des risques et un plan de projet.
  2. Élaboration :
    • Définir, valider et arrêter l'architecture; démontrer son efficacité, et planifier la phase de construction.
    • Produit 80% du modèle de cas d'utilisation, une description de l'architecture, un exécutable de validation de l'architecture.
  3. Construction :
    • Développement du logiciel par incréments successifs, optimisant les ressources et maintenant la qualité.
    • Produit des versions exécutables du logiciel et des manuels d'utilisation.
  4. Transition :
    • Déploiement du logiciel, prise en charge des problèmes et atteinte d'un niveau de stabilité pour les utilisateurs.
    • Produit la version finale du logiciel et les manuels d'utilisation.
Activités RUP

Chaque itération comprend plusieurs activités répétées :

  • Modélisation métier : Comprendre l'organisation cliente, réaliser un glossaire, cartographier les processus.
  • Expression des besoins : Cibler les besoins utilisateurs/client avec des cas d'utilisation, des scénarios, des maquettes.
  • Analyse : Transformer les besoins utilisateur en modèles UML neutres vis-à-vis de la technologie.
  • Conception : Modéliser le fonctionnement du système, incluant les exigences non fonctionnelles et les choix technologiques.
  • Implémentation : Développer le système par composants, retouchant les modèles si nécessaire.
  • Test : Vérifier les résultats de l'implémentation (tests unitaires et d'intégration).
  • Déploiement : Mettre en place le logiciel, peut inclure des activités de prototypage pour valider l'architecture physique et les choix technologiques.

eXtreme Programming (XP)

Méthode agile axée sur des pratiques extrêmes, privilégiant la réactivité et la collaboration.

  • Valeurs prioritaires :
    • Personnes et interactions > procédures et outils.
    • Applications fonctionnelles > documentation pléthorique.
    • Collaboration client > négociation de contrat.
    • Acceptation du changement > planification.
  • Méthode exigeante en discipline et communication, mais efficace pour la rapidité et la qualité.
  • Favorise le feedback constant pour corriger la trajectoire du projet.
13 Pratiques XP
  • Gestion de projets :
    • Livraisons fréquentes : Mises en production rapides.
    • Planification itérative : Révision constante du plan.
    • Client sur site : Le client fait partie de l'équipe.
    • Rythme durable : Pas plus de 40h/semaine.
  • Programmation :
    • Conception simple : Peu de développements anticipés.
    • Remaniement (refactoring) : Code réorganisé pour la clarté.
    • Tests unitaires : Développement de tests de non-régression.
    • Tests de recette : Tests fonctionnels automatisés.
  • Collaboration :
    • Responsabilité collective du code : Tout développeur peut travailler sur toute partie du code.
    • Programmation en binômes : Travail en duo, binômes renouvelés.
    • Règles de codage : Strictes et définies par l'équipe.
    • Métaphore : Description commune du design.
    • Intégration continue : Intégration quotidienne des développements.
Déroulement du projet XP
  1. Exploration : Questions techniques, user stories du client, estimations des temps de développement.
  2. Planification de la première release : Fonctionnalités essentielles, durée de 2 à 6 mois.
  3. Itérations de production : Développement par sous-ensembles de fonctionnalités (1 à 4 semaines), tests fonctionnels.
  4. Mise en production : Logiciel fonctionnel, tests constants, réglages de performance.
  5. Maintenance : Ajout de fonctionnalités secondaires.
  6. Mort du projet : Quand tous les besoins sont remplis ou que le système n'est plus rentable.
Rôles de l'équipe XP
  • Développeur : Programmation, tests unitaires (conception et programmation).
  • Client : Décrit et maîtrise les scénarios, spécifie les tests fonctionnels, définit les priorités.
  • Testeur : Écrit les tests de recette automatisés.
  • Tracker : Suit le planning et les estimations.
  • Manager : Responsable du projet (satisfaction client, planning, ressources).
  • Coach : Garant du processus XP, organise les planifications, favorise la créativité.
Avantages et inconvénients
  • XP : Léger, pour petits projets (max 12 personnes). Inconvénients : focalisation individuelle, manque de contrôle, risques de dérive.
  • RUP : Lourd, pour gros projets nécessitant beaucoup de documentation. Inconvénients : "usine à gaz", difficulté de mise en œuvre spécifique.

Modélisation avancée avec UML

Expression de contraintes avec OCL (Object Constraint Language)

UML exprime des contraintes graphiquement ou via des propriétés prédéfinies, mais cela peut être insuffisant pour des contraintes complexes.

Le texte libre dans les notes UML est simple et compréhensible, essentiel pour documenter les contraintes. Cependant, il peut être ambigu, imprécis et difficile à lier aux éléments du modèle.

OCL est un langage de requêtes et de contraintes textuel, fortement typé, sans effets de bords. Il est intégré à UML pour exprimer des contraintes non exprimables graphiquement, le rendant plus précis. Ce n'est pas un langage de programmation, mais de spécification, permettant de détecter les erreurs tôt.

Points forts et faibles de OCL
  • Faibles : Moins rigoureux que des langages formels (VDM, Z, B), pas de preuves formelles dans tous les cas, puissance d'expression limitée.
  • Forts : Simple à écrire et comprendre, très bien intégré à UML, bon compromis simplicité/puissance, passage vers différentes plateformes technologiques.
Contextes de contraintes OCL

Une contrainte est toujours associée à un élément de modèle (son contexte), spécifié par :

  • Entre accolades {...} dans une note.
  • Avec le mot-clé context.
Types de prédicats OCL
  • inv : Invariants de classes (doivent être toujours vrais).
  • pre : Pré-conditions d'opérations (doivent être vraies avant l'exécution).
  • post : Post-conditions d'opérations (doivent être vraies après l'exécution).
    • @pre : Référence la valeur avant l'opération.
    • result : Résultat de l'opération.
    • oclIsNew() : Indique si un objet n'existait pas.
Définition d'éléments OCL
  • def : Déclarer de nouveaux attributs ou opérations dans une classe.
  • init : Spécifier la valeur initiale des attributs.
  • body : Exprimer le corps des méthodes {query}.
  • derive : Définir des éléments dérivés.
Accès et navigation en OCL
  • Accès à un attribut : objet.attribut.
  • Accès à une méthode : objet.operation(param1, ...).
  • Accès à un ensemble d'objets liés : objet.nomderole. Le résultat peut être une valeur ou un ensemble, selon la multiplicité ciblée.
    • size(), isEmpty(), notEmpty().
    • Si l'association est réflexive, utiliser objet.nomAssociation[nomDeRole].
    • Accès qualifié : lien.nomderole[valeur1, valeur2, ...].
Opérateurs et types primitifs OCL
  • Opérateurs :
    • . : Accès à une propriété d'un objet.
    • -> : Accès à une propriété d'une collection.
    • :: : Accès à un élément d'un paquetage/classe.
    • if cond then expr else expr endif.
  • Types primitifs :
    • Integer : +, -, *, div, mod, abs, max, min.
    • Real : +, -, *, /, floor, round, max, min.
    • Boolean : not, and, or, xor, implies, if-then-else-endif (évaluation partielle).
    • String : s.size(), s1.concat(s2), s1.substring(i1,i2), s.toUpper(), s.toLower().
    • Enumération : Ex: Jour::Mardi.
Opérations sur les collections OCL
  • Types de collections : Set(T), OrderedSet(T), Bag(T), Sequence(T).
  • Opérations courantes : size(), isEmpty(), nonEmpty(), count(elem), includes(elem), excludes(elem), includesAll(coll), excludesAll(coll), sum().
  • Manipulation : union(ens), difference(ens), including(elem), excluding(elem), asSequence(), asBag(), asOrderedSet().
  • Filtrage et sélection :
    • select(cond) : Retient les éléments.
    • reject(cond) : Élimine les éléments.
    • any(cond) : Sélectionne un élément (non déterministe).
    • forAll(cond) : Quantificateur universel.
    • exists(cond) : Quantificateur existentiel.
    • isUnique(expr) : Retourne vrai si l'expression a une valeur différente pour chaque élément (utile pour les clés de BD).
  • Tuples : Champs nommés sans ordre. Tuple{x=-1.5, y=12.6}. À partir d'UML 2.0.
  • Collections imbriquées : Imbrications arbitraires de constructeurs de types (à partir d'UML 2.0).
    • collect : Met à plat les collections (utile pour la navigation).
    • collectNested : Conserve l’imbrication.
  • Itérateur iterate : Le plus général, les autres itérateurs en sont des cas particuliers.
  • Tri des collections : sortedBy(expr).

Diagrammes d'états-transitions

Décrivent la séquence d'états qu'un objet subira durant son cycle de vie. Un automate à états finis représente le comportement d'un classeur dont les sorties dépendent de ses entrées et de son historique.

  • Les états sont des rectangles aux coins arrondis, les transitions sont des arcs orientés.
  • Des états «composites» peuvent contenir des sous-diagrammes.
  • Chaque diagramme d'états ne concerne qu'une seule classe. Chaque automate s'exécute concurremment.
  • État initial : Point de départ (cercle rempli).
  • État final : Fin de l'exécution (double cercle).
Événements déclencheurs
  • Call : Appel de méthode sur l'objet courant.
  • Change : Passage de faux à vrai d'une condition booléenne (when(conditionBoolean)).
  • Signal : Réception d'un signal asynchrone (classe stéréotypée <<signal>>).
  • After : Écoulement d'une durée (after(duree)).

Syntaxe d'une transition : nomEvenement(params) [garde] / activite.

  • La garde est une condition pour déclencher la transition.
  • L'activité sont des instructions à effectuer.
Alternatives de transition
  • Points de jonction (petit cercle plein) : Partagent des segments de transition, un raccourci d'écriture. Toutes les gardes le long du chemin doivent être vraies dès le franchissement du premier segment.
  • Points de choix (losange) : Évaluent les gardes au moment où le point est atteint, permettant de baser le choix sur les résultats précédents. Ce n'est pas un simple raccourci.
Transitions internes et états composites
  • Une transition interne ne modifie pas l'état courant. Les déclencheurs entry/, do/, exit/ définissent des activités à l'entrée, durant, ou à la sortie de l'état.
  • Un état composite est décomposé en sous-états imbriqués.
  • Les transitions peuvent cibler la frontière d'un état composite (cible : état initial) ou avoir pour source cette frontière (s'applique à tous les sous-états).
  • Un pseudo-état historique (H cerclé) cible le dernier état visité. H* désigne un historique profond.
  • Les points de connexion (X pour sortie, vide pour entrée) permettent d'abstraire les sous-états.
Concurrence et synchronisation
  • Plusieurs automates peuvent s'exécuter indépendamment avec un séparateur en pointillés, créant des états concurrents.
  • Une transition fork crée deux états concurrents.
  • Une transition join est une barrière de synchronisation qui supprime la concurrence. Toutes les tâches doivent être prêtes pour continuer.

Diagrammes d'activités

Offrent une manière graphique de modéliser les traitements, comme le comportement d'une méthode ou le déroulement d'un cas d'utilisation. Ressemblent aux états-transitions, mais avec une interprétation différente.

  • Décrivent le comportement d'une application de manière plus fluide que les diagrammes d'états.
  • Sont pertinents pour la modélisation des processus métier complexes ou des flux de travail.
  • La vision des diagrammes d'activités se rapproche des langages de programmation impérative.
Activités et transitions
  • Les activités décrivent un traitement, le flot de contrôle reste jusqu'à la fin. Peuvent être locales ou composites.
  • Les transitions (flèches pleines) connectent les activités et sont déclenchées à la fin de l'activité source. Elles sont atomiques.
  • Les gardes conditionnelles permettent d'exprimer des conditions. Les points de choix (losanges) sont utilisés pour mieux représenter un branchement.
  • Les activités structurées utilisent les structures de contrôle usuelles (conditionnelles et boucles) avec des arguments d'entrée et de sortie.
  • Les partitions attribuent les activités à des éléments particuliers du modèle (classeurs).
Flot de données

Le flot de données est représenté par :

  • Les pins : Points de connexion pour une action, qui doit recevoir des valeurs pour commencer et en affecter en sortie.
  • Les flots d'objets : Passage de données entre activités, représentés par un arc entre pins.
    • Peuvent porter des annotations <<transformation>> ou <<selection>>.
  • Les nœuds d'objets : Conteneurs typés pour le transit des données.
Concurrence et synchronisation
  • Les barres de synchronisation créent des flots concurrents (fork) ou les synchronisent (join).
  • Les nœuds de contrôle de type « flow final » détruisent un flot de contrôle sans affecter les autres. Le nœud de contrôle final interrompt et détruit tous les flots de contrôle de l'activité.
Actions de communication
  • Gèrent le passage de paramètres et les mécanismes d'appels (synchrones et asynchrones).
  • Call operation : Appel d'une opération sur un classeur.
  • Call behavior : Invocation d'un comportement spécifié par un diagramme UML.
  • Send : Envoi de messages asynchrones (ex: broadcast signal). L'action symétrique est accept event.
Exceptions et régions interruptibles
  • Les exceptions : Interrompent un traitement en cas de déviation. Utilisent des pins d'exception (triangle) et des flèches en "zigzag".
  • Les régions interruptibles : Cadre arrondi en pointillés. Si l'événement d'interruption survient, toutes les activités en cours sont stoppées.
Modes d'exécution
  • Parallel : Exécution indépendante ou simultanée.
  • Iterative : Exécution séquentielle selon l'ordre d'entrée.
  • Stream : Les éléments sont passés en flux de données.

Diagrammes de communication

Les diagrammes de communication et de séquences sont des types de diagrammes d'interaction. Les diagrammes de communication offrent une représentation spatiale des lignes de vie, tandis que les diagrammes de séquences mettent l'accent sur l'ordre temporel.

  • Un rôle correspond à une ligne de vie.
  • Les connecteurs relient les lignes de vie.
Messages
  • Synchrone et asynchrone, comme dans les diagrammes de séquences.
  • Les flèches des messages sont tracées à côté des connecteurs.
  • Les numéros de séquence (1, 2, 3... ou 1.1, 1.2...) représentent l'ordre chronologique et l'emboîtement.
  • Les messages parallèles sont numérotés avec des lettres (1.a, 1.b...).
  • Pas d'opérateurs combinés, mais des clauses d'itération (*[i:=1..n]) ou de choix (*[condition]).
  • La syntaxe complète est : numeroSéquence [expression] : message.
Collaborations
  • Montrent des instances qui collaborent pour une fonctionnalité.
  • Représentées par une ellipse pointillée avec deux compartiments ou une ellipse simple avec les rôles liés.
  • Les collaborations organisent les interactions, qui sont documentées par les diagrammes de communication ou de séquence.

Diagrammes de composants et de déploiement

Diagrammes de composants

Décrivent l'architecture logicielle du système.

  • Un composant logiciel est une unité logicielle autonome, munie d'interfaces requises ou offertes (représenté par un rectangle avec deux petits rectangles sur le côté gauche).
  • Les composants peuvent être décomposés en sous-composants.
  • Les liens entre composants sont des dépendances entre leurs interfaces (boules de caviar pour interface offerte, "sucettes" pour interface requise).
  • Le "câblage interne" est spécifié par des connecteurs de délégation (reliant un port externe à un port d'un sous-composant).
  • Permettent de structurer l'architecture logicielle, d'intégrer des briques logicielles tierces et d'identifier des composants réutilisables.
  • Un composant est un espace de noms pour organiser les éléments de conception, les cas d'utilisation, les interactions et le code.

Diagrammes de déploiement

Représentent l'environnement d'exécution du système sur des ressources matérielles.

  • Un nœud : Ressource (matérielle ou logicielle) sur laquelle des artefacts peuvent être déployés. Représenté par un cube.
  • Un artefact : Entité physique du monde réel (ex: exécutable, fichier, document). Représenté comme une classe avec le mot-clé <<artefact>>.
  • Un artefact déployé sur un nœud est symbolisé par une flèche en trait pointillé <<déployé>>. L'artefact peut aussi être inclus dans le cube du nœud.
  • Les noms des instances de nœuds et d'artefacts sont soulignés.
  • Les flèches de dépendance montrent la capacité d'un nœud à prendre en charge un type de composant.

Bonnes pratiques de la modélisation objet : Design Patterns

Les patrons de conception (Design Patterns) sont des solutions classiques à des problèmes récurrents en conception logicielle. Le concept a été formalisé par Christopher Alexander en architecture, puis adapté à la COO par le GOF (Erich Gamma, Richard Helm, Ralph Johnson et John Vlissides).

  • Un pattern n'est pas une brique, une règle ou une méthode; c'est une technique d'architecture logicielle qui offre une solution éprouvée.
Éléments de description d'un pattern
  • Nom : Résume le problème.
  • Intention : Décrit les objectifs.
  • Indications d'utilisation : Cas où le pattern est utile.
  • Motivation : Cas particulier illustrant le pattern.
  • Structure : Représentation graphique des classes.
Avantages et inconvénients des Design Patterns
  • Avantages : Capitalisation de l'expérience, conception plus rapide, meilleure qualité, réduction des erreurs, communication facilitée, apprentissage.
  • Inconvénients : Nécessité d'effort de synthèse, apprentissage et expérience, risque de surutilisation, multiplicité des patterns.
Catégories de Design Patterns (GOF)
  1. Patrons de création : Gèrent l'instanciation et la configuration des objets, encapsulant la connaissance de la classe concrète qui instancie.
    • Exemples : Abstract Factory, Builder, Factory Method, Prototype, Singleton.
    • Singleton : Garantit qu'une classe n'a qu'une seule instance et fournit un point d'accès global.
      • Motivation : Spooler d'impression, gestionnaire d'affichage.
  2. Patrons de structure : Définissent l'usage des classes et objets dans des grandes structures, séparant interface et implémentation.
    • Exemples : Adapter, Bridge, Composite, Decorator, Facade, Flyweight, Proxy.
    • Adapter : Convertit l'interface d'une classe pour qu'elle corresponde aux attentes d'un client.
    • Bridge : Découple une abstraction de son implémentation.
    • Composite : Permet de traiter de la même manière des objets atomiques et des combinaisons d'objets.
  3. Patrons de comportement : Décrivent les algorithmes, les comportements entre objets et les formes de communication.
    • Exemples : Chain of Responsibility, Command, Interpreter, Iterator, Mediator, Memento, Observer, State, Strategy, Template Method, Visitor.
    • Observer : Définit une dépendance "un à plusieurs", où un changement d'état d'un objet notifie et met à jour d'autres objets.
    • Strategy : Définit une famille d'algorithmes, les encapsule et les rend interchangeables.

Les design patterns sont des éléments de conception qui doivent être combinés judicieusement. Une utilisation abusive peut nuire à la lisibilité.

Bir quiz başla

Bilgini etkileşimli sorularla test et