36
CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours Qualité, Modularité • Découplage Abstraction fonctionnelle Abstraction de données Rappel : encapsulation

CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

Embed Size (px)

Citation preview

Page 1: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 1

Conception et Programmation à ObjetsCours 1

Eléments de conception logicielle Mikal ZIANE

• Organisation et objectifs du cours• Qualité, Modularité• Découplage• Abstraction fonctionnelle• Abstraction de données• Rappel : encapsulation

Page 2: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 2

Organisation

• IntervenantsDenis Poitrenaud (TD) Mikal Ziane (cours et TD) email: [email protected]

• Volume horaire– 1h30 Cours / semaine *10– 1h30 TD ou TP * 9 (6 TD et 3 TP)

• Contrôle des connaissances– participation aux cours/TD (présence + activité)– 1 projet coefficient 1

• la participation modifie la note de projet (bonus ou malus)– 1 DST 3H avec documents coefficient 3

• Matériel et logiciel : Eclipse (Windows ou Linux)

• Supports (transparents des cours + énoncés et corrigés des TD + sujets examens + sujets projets) disponibles sous forme électronique sur le répertoire commun Objets C++

Page 3: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 3

Conseils

• Passez sur machine les exemples du cours et des TD et expérimentez.

• Faites le projet dès que possible. Il y aura des étapes intermédiaires.

• N'hésitez pas à poser des questions !

Page 4: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 4

Objectifs du Cours

• Comprendre les enjeux de la qualité du logiciel.• Maîtriser les notions de base sur la conception des

programmes et les méthodes de développement agile.• Assimiler les concepts principaux de la programmation par

objets.• Savoir les exprimer dans un langage de programmation

(C++ cette année)

Page 5: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 5

Prérequis

• Algorithmique de base

• Maîtrise parfaite des fonctions

• Gestion mémoire de base

• Encapsulation

• Classes et méthodes en C++

• Templates et STL (notions de base)

Page 6: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 6

Plan du trimestre

• Eléments de conception logicielle [1 cours + 1 TD]

• Méthodes agiles (distribution du projet) [1 cours + 1 TD]

• Standard Template Library (STL) [1 cours + 1 TP]

• Héritage et polymorphisme [3 cours + 3 TD]

• Gestion des exceptions [1 cours + 1 TP]

• Gestion mémoire [1 cours + 1 TP]

• Révisions [ 1 cours ]

Page 7: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 7

La Crise du Logiciel

• Les logiciels coûtent trop cher• Les logiciels sont de mauvaise qualité (bogues …)• C’est le coût de maintenance qui pèse le plus lourd :

– Un logiciel vit 10 ans en moyenne– Quand le logiciel est « fini » on n’a dépensé que 1/3 du coût total !

• La maintenance est trop difficile– logiciels trop complexes– logiciels trop rigides (difficiles à modifier)

• Les deux défis du concepteur :– maîtriser la complexité– maîtriser les changements

Page 8: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 8

Le bon et le mauvais programmeurLe mauvais

• Est sûr d'être le meilleur programmeur du monde

• Écrit un programme incompréhensible pour montrer sa supériorité

• Utilise un maximum de ruses et de trucs bizarres (le côté obscur)

• "Optimise" chaque ligne de code !• Pense que l’analyse et la conception ça ne sert

à rien• Fait de suite un programme compliqué• Fait soit pas de documentation du tout soit

une documentation pléthorique• Fait tout le projet seul parce que son

camarade de binôme est nul (ou l’inverse)• Change tout son programme dès qu'il y a une

modification à faire ou au contraire essaye de rendre son programme super hyper modifiable (et échoue)

Le bon• Ecrit des programmes faciles à comprendre• Prévoie les tests dès le début du projet• N’optimise éventuellement son programme

qu’une fois testé• Optimise là où ca fait mal• Sait que les phases d’analyse et de

conception sont essentielles• Commence par faire des prototypes simples• Documente les aspects importants• Dialogue avec tous les partenaires du projet• Rend son programme suffisamment flexible

(mais pas plus) s'il faut faire face à une modification

Page 9: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 9

Attention si vous passez du côté obscur

Obi-ziane Kenobi

Page 10: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 10

Découper en modules

• "code spaghetti" ou architecture logicielle ?• Architecture logicielle : ensemble de modules (ou de

composants) reliés entre eux.• Différentes sortes de modules : fonctions, classes,

packages…• Découper en modules casse la complexité MAIS :

– Attention aux modules trop compliqués (les découper)– Si on découpe trop on obtient trop de modules (les regrouper)– Attention aux découpages arbitraires (un module doit être

cohérent)

Page 11: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 11

Logiciel spaghettitiré de v3ga.net/blog/

Page 12: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 12

Exemple d'architecture logicielletiré de http://www.webengine.be/architecture/

Page 13: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 13

Qu'est-ce qu'un module ?

• Un module est une partie d'une application comprenant :– un nom– une interface– une sémantique– une implémentation

• Un module est utilisé par des programmeurs clients et réalisé par un programmeur implémenteur

• L'implémentation du module réalise un contrat entre clients et implémenteur

• Ce contrat est constitué par l'interface et la sémantique• Dans ce cours les modules seront en général des classes (mais

chaque méthode est aussi un sous-module).

Page 14: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 14

double racineCarree (double x, double e);

// si (x>=0 et e >0)

// abs(racineCarree(x,e)*racineCarree(x,e) - x) <= e

double racineCarree (double x, double e)

{ assert (x >=0);

assert (e >0);

// calculer et retourner un résultat approché

}

Un tout petit module

nom et interface

implémentation

sémantique

Page 15: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 15

Éviter les couplages dangereux

• Certaines modifications du cahier des charges semblent locales : ne concernent apparemment qu’un module M.

• Il faut limiter la propagation de la modification vers les modules clients de M.

• La propagation a lieu quand le client dépend d’un élément syntaxique (type, méthode, attribut …) qui est modifié.

• Le client dépend d’un élément s’il le mentionne explicitement (utilise son nom).

• On dit alors qu’il y a un couplage fort entre le client et M.

Page 16: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 16

Comment utiliser un élément instable?

• Seules les dépendances envers des éléments instables (qui risquent d’être modifiés) sont dangereuses.

• Chaque fois que l’élément instable est modifié le code des tous les clients doit l’être aussi !

• Heureusement : on peut souvent utiliser un élément sans le mentionner directement : grâce à une indirection !

• Une indirection est souvent une abstraction.

Page 17: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 17

Indirection : évite les couplages dangereux

Terme A

Terme B1

Terme A

Terme Bn…

Terme B1 Terme Bn…

Indirection

L'indirection introduit une articulation : on peut changer A sans affecter B1.. Bn

Page 18: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 18

Exemples de couplages inutiles (corrigez)

1. int i, tab[10];for (i =0; i <10; ++i)

cin >> tab[i];

2. string noms[2]={"chien", "chat"};int i; for (i=0; i <2; ++i)

cout << noms[i] << endl;

3. cout << "Choisisez le type d'animal : ";cout << "Chien (1) Chat (2)" << endl;

4. string nom; // un chien on un chat

Page 19: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 19

corrigez (suite)

5. switch(animal->getType()) { case CHIEN : cout << "aboie"; break; case CHAT : cout << "miaule"; break; }

6. class BatailleNavale {public:

BatailleNavale (); // remplit le tableau tab// à false

…private:

bool tab[10][10];};

Page 20: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 20

Dépendences en rouge

1. int i,tab[10];for (i =0; i <10; ++i)

cin >> tab[i];

2. string noms[2]={"chien", "chat"};int i; for (i=0; i <2; ++i)

cout << noms[i] << endl;

3. cout << "Choisisez le type d'animal : ";cout << "Chien (1) Chat (2)" << endl;

4. string nom; // un chien on un chat

Page 21: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 21

Dépendences en rouge (suite)

5. switch(animal->getType()) { case CHIEN : cout << "aboie"; break; case CHAT : cout << "miaule"; break; }

6. class BatailleNavale {public:

BatailleNavale (); // remplit le tableau tab

// à false …private:

bool tab[10][10]; };

Page 22: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 22

Correction1. enum {taille =10}; // ou const int taille = 10;

int i,tab[taille]; for (i =0; i <taille; ++i)

cin >> tab[i];

2. string noms[]={"chien", "chat"};enum {taille=sizeof(noms)/sizeof(*noms)};int i; for (i=0; i <taille; ++i)

cout << noms[i] << endl;

3. cout << "Choisisez le type d'animal : ";int i;for (i=0; i <taille; ++i)

cout << noms[i] << '(' << i << ") ";cout << endl;

4. string nom;

Page 23: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 23

correction (suite)

4. remplacer le switch par liaison dynamique (cf. cours 4,5,6)

5. class BatailleNavale {public:

BatailleNavale (); // crée un terrain vide

…private: enum {largeur=10, hauteur =10};

bool tab[largeur][hauteur]; };

Page 24: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 24

Qu’est-ce qu’une abstraction fonctionnelle ?• Que fait ce programme ? • Quelles abstractions peut-on dégager ? Pour quoi faire ?int exemple1(){ int tab[4] = {5,12,8,7}; int i; for (i =0; i<4; i++) for (int j=i+1; j<4; j++) if (tab[i] > tab[j]) { int x = tab[i]; tab[i] = tab[j]; tab[j] = x; } for (i=0; i<4; i++) cout << tab[i] << " "; cout << endl;}

Page 25: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 25

void trier (int tab[], int n){ int i,j,x; for (i =0; i<n; i++) for (j=i+1; j<n; j++) if (tab[i] > tab[j]) { x = tab[i]; tab[i] = tab[j]; tab[j] = x;}}void afficher (int tab[], int n){ int i; for (i=0; i<n; i++) cout << tab[i] << " "; cout << endl; }int exemple1(){ int tab[] = {5,12,8,7}; enum {taille = sizeof(tab)/sizeof(*tab)}; trier(tab,taille); afficher(tab,taille); return 0}

Version améliorée

Page 26: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 26

Intérêt des fonctions

• Indirection (on fait un détour)– on peut changer l’algorithme sans changer le code appelant

– on factorise le code à un seul endroit• modification beaucoup plus facile

• uniformité facilité

• Abstraction (on cache les détails)– code appelant plus simple

– code appelant plus clair

• Généricité, réutilisation– on peut appliquer le code avec différents paramètres

• Désavantage (parfois) : coût en temps et en mémoire

Page 27: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 27

Qu’est-ce qu’une abstraction de données ?• Que fait exemple2 ?

• Quelles abstractions peut-on dégager ?

• Pourquoi définir ces abstractions ?const int taille = 5;

void exemple2()

{ char tab[taille];

int i = -1;

while (i != taille -1)

{ i++;

tab[i] = 'a' +i;

}

while (i != -1)

cout << tab[i--] << " ";

cout << endl;

}

Page 28: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 28

Exemple 2 un peu amélioré

const int taille = 5;

struct sPile { char tab[taille]; int dernier;};

void init(sPile&);bool pleine (const sPile&);bool vide (const sPile&);void empiler (sPile&, char);char depiler (sPile&);

Page 29: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 29

void exemple2Mieux(){ sPile p; init(p); char c; for (c='a';! pleine(p); c++) empiler(p,c); while (! vide(p)) cout << depiler(p) << " "; cout << endl;}

Page 30: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 30

Rappel: définition de l'encapsulation

• Un module encapsule ses données si les programmeurs CLIENTS ne peuvent pas y accéder sans passer par les fonctions de l’interface

• Exercice : trouvez les violations d'encapsulation ci-dessous

void bad (){ sPile p; p.dernier = -1;

char c; for (c='a';! pleine(p); c++) empiler(p,c); while ( p.dernier != -1)

cout << p.tab[--p.dernier] << " " ; cout << endl;}

Page 31: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 31

void bad (){ sPile p; p.dernier = -1; char c; for (c='a';! pleine(p); c++) empiler(p,c); while ( p.dernier != -1)

cout << p.tab[--p.dernier] << " " ; cout << endl;}

Pour empêcher ce qui est en gras : mettre les données en privé dans une classe

Page 32: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 32

class Pile {public: Pile (); void empiler (char); char depiler (); bool estPleine () const; bool estVide () const;private: enum {taille = 5}; // mieux qu'un #define char tab[taille]; int dernier; };

Exemple2 encore mieux

Page 33: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 33

Intérêts de l'encapsulation: clarté

• Il est plus facile de comprendre ça:p.empiler(3)• que ça:p.tab[++ p.dernier] =3;

• La clarté est souvent négligée par les débutants.• Elle facilite pourtant la maintenance.• Elle diminue aussi le nombre du bugs.

Page 34: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 34

Intérêt de l’encapsulation: protection

• Sans encapsulation, il est facile pour le programmeur client de corrompre les données des modules qu’il utilise.

• L’encapsulation lutte radicalement contre ce genre de bug:– en le détectant dès la source– sinon ils peuvent être très difficiles à corriger.

• Exemple: p.dernier = 100;• Cette instruction n'a pas de sens pour une pile de 10 postes.• Pourtant sans encapsulation, elle compile n'importe où !• Grâce à l'encapsulation une telle erreur ne peut se produire que

dans une méthode de Pile.

Page 35: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 35

Protection (suite)

• Grâce à l'encapsulation:

si un objet est vérolé (dans un état anormal), il suffit de regarder dans 1 fichier pour trouver le bug !

• Il y a donc à la fois – beaucoup moins de risque de faire ce genre de bugs – beaucoup plus de facilité à les résoudre.

• L'utilisation de préconditions et postconditions permet encore de réduire les risques de bugs.

Page 36: CPO 2006 - Cours 1 page 1 Conception et Programmation à Objets Cours 1 Eléments de conception logicielle Mikal ZIANE Organisation et objectifs du cours

CPO 2006 - Cours 1

page 36

Intérêt de l’encapsulation: Modifications

• Bogue de l’an 2000• On peut modifier l’implémentation d’une classe sans

toucher au code client !• Or le code client est en général beaucoup plus gros que

le code d’une seule classe.• Exemple:p.tab[++ p.dernier] =3;• Et si on implémente la pile avec une liste chaînée ?• Ceci reste valable :p.empiler(3)