IdentifiantMot de passe
Loading...
Mot de passe oubli� ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les r�ponses en temps r�el, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++ Discussion :

Adaptation Modern C++ sur du Legacy Code


Sujet :

C++

  1. #1
    Membre confirm�
    Profil pro
    Enseignant
    Inscrit en
    Septembre 2011
    Messages
    43
    D�tails du profil
    Informations personnelles :
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activit� : Enseignant

    Informations forums :
    Inscription : Septembre 2011
    Messages : 43
    Par d�faut Adaptation Modern C++ sur du Legacy Code
    Bonjour !

    Je dois maintenir une application construite avant le C++11. L�application fonctionne grosso modo de cette fa�on :

    Voici le code d'avant :

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
     
    #include <iostream>
    #include <list>
     
    class A  // construite pour l'exemple ...
    {
    public:
    	A(int _nbr, int _valeur){
    		nbr=_nbr; valeur =_valeur;
    	}
    	~A(){};
     
    	int getNbr() {return nbr;}  // pour avoir des fonctions à utiliser
    	int getValue() {return valeur;}  // pour avoir des fonctions à utiliser
    	void setValue(int _v) { valeur = _v;}  // pour avoir des fonctions à utiliser
    private:
    	int nbr;
    	int valeur;
    };
     
     
    int main(int argc, char **argv)
    {
    	std::list<A*> myList;
    	A* tmp = nullptr;
     
    	//creation avec new
    	for(int i=0;i<7; i++)
    		myList.push_back(new A(i, 3*i-1));
     
    	// affichage de la liste
    	for(auto l : myList)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//suppression des éléments impairs
    	for(auto it = myList.begin(); it !=myList.end(); it++) {
    		if ((*it)->getNbr()%2) {
    			delete (*it);
    			myList.erase(it);
    			it--;
    		}
    	}
     
    	// recherche d'un élément particulier i=4
    	for(auto it = myList.begin(); it !=myList.end(); it++) {
    		if ((*it)->getNbr()==4) {
    			tmp = (*it);
    			break;
    		}
    	}
    	// plus tard ... modification de l'élément tmp
    	if (tmp != nullptr) {
    		tmp->setValue(-8);
    	}
     
    	// affichage de la liste
    	for(auto l : myList)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//suppression totale
    	for(auto it = myList.begin(); it !=myList.end(); it++) {
    			delete (*it);
    			myList.erase(it);
    			it--;
    	}
    	myList.clear();
     
    	return 0;
    }

    J'ai travaill� sur le code et les smart-pointers afin de r�duire la dette technique du logiciel :

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
     
    #include <iostream>
    #include <list>
    #include <memory>
    #include <algorithm>
     
    class A // construite pour l'exemple ...
    {
    public:
    	A(int _nbr, int _valeur){
    		nbr=_nbr; valeur =_valeur;
    	}
    	~A(){};
    	int getNbr() {return nbr;}  // pour avoir des fonctions à utiliser
    	int getValue() {return valeur;}  // pour avoir des fonctions à utiliser
    	void setValue(int _v) { valeur = _v;}  // pour avoir des fonctions à utiliser
    private:
    	int nbr;
    	int valeur;
    };
     
     
    int main(int argc, char **argv)
    {
    	std::list< std::shared_ptr<A> > myList;
    	std::shared_ptr<A> tmp;
     
    	//creation d'élements dans une liste
    	for(int i=0;i<7; i++)
    		myList.push_back( std::make_shared<A>(i, 3*i-1) );
     
    	// affichage de la liste
    	for(auto l : myList)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//suppression des éléments impairs
    	myList.remove_if( [](std::shared_ptr<A> a) { return a->getNbr()%2; } );
     
    	//recherche d'un élément particulier i=4
    	auto it = find_if(myList.begin(), myList.end(), [](std::shared_ptr<A> a) { return a->getNbr()==4; } );
    	if (it != myList.end())
    		tmp = (*it);
     
    	//plus tard ... modification de l'élément tmp
    	if (tmp != nullptr)
    		tmp->setValue(-8);
     
    	// affichage de la liste
    	for(auto l : myList)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//suppression totale
    	myList.clear();
     
    	return 0;
    }
    Je me suis d�barrass� de la gestion des pointeurs et cela me ravit.

    Toutefois, est ce que je peux encore am�liorer mon travail en C++ "moderne" sur cet exemple ?

    Je vous en remercie d'avance !

  2. #2
    Expert confirm�
    Homme Profil pro
    Ing�nieur d�veloppement mat�riel �lectronique
    Inscrit en
    D�cembre 2015
    Messages
    1 599
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 62
    Localisation : France, Bouches du Rh�ne (Provence Alpes C�te d'Azur)

    Informations professionnelles :
    Activit� : Ing�nieur d�veloppement mat�riel �lectronique
    Secteur : High Tech - �lectronique et micro-�lectronique

    Informations forums :
    Inscription : D�cembre 2015
    Messages : 1 599
    Par d�faut
    Bonjour,
    • remove_if() ne fait pas ce que tu crois, il ne supprime rien!
    • utiliser des unique_ptr<> plut�t que des shared_ptr<> serait nettement plus optimum. Mais tu verras alors des lignes qui ne fonctionneront plus car elles n'�taient pas optimales. Par exemple l'utilisation de tmp serait � reposer.
    • Il y des param�tres pass�s par valeur, il faut penser utiliser le passage par r�f�rence quand il est utile.
    • la fonction clear() ne sert plus � rien car l'objet dispara�t d�s la ligne suivante

  3. #3
    R�dacteur/Mod�rateur


    Homme Profil pro
    Network game programmer
    Inscrit en
    Juin 2010
    Messages
    7 153
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 38
    Localisation : Canada

    Informations professionnelles :
    Activit� : Network game programmer

    Informations forums :
    Inscription : Juin 2010
    Messages : 7 153
    Billets dans le blog
    4
    Par d�faut
    - for(auto l : myList) fait une copie et donc une incr�mentation/d�cr�mentation du compteur de r�f�rence pour chaque objet
    - Les shared_ptr ne remplacent pas des pointeurs nus, unique_ptr oui
    - Ne pas manipuler d'objets dynamiques serait encore mieux
    - vector est pr�f�rable � list
    Pensez � consulter la FAQ ou les cours et tutoriels de la section C++.
    Un peu de programmation r�seau ?
    Aucune aide via MP ne sera dispens�e. Merci d'utiliser les forums pr�vus � cet effet.

  4. #4
    Membre confirm�
    Profil pro
    Enseignant
    Inscrit en
    Septembre 2011
    Messages
    43
    D�tails du profil
    Informations personnelles :
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activit� : Enseignant

    Informations forums :
    Inscription : Septembre 2011
    Messages : 43
    Par d�faut
    Bonjour et merci pour votre r�ponse !

    Pour le remove_if, je ne savais pas et je ne comprenais pas. Lorsque j'�crivais cela:

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    ~A() { std::cout << "destruction de " << nbr << std::endl;}
     
    myList.remove_if( [](std::shared_ptr<A> a) { return a->getNbr()%2; } );
    La liste des objets supprim�s s�affichait � l'�cran apr�s le remove_if.

    Je viens de relire encore la doc et si j'ai compris, remove_if ne fait que de d�placer des objets mais qu'il ne les supprimait pas. Et si j'ai bien compris, les objets apparaissent comme supprim� car justement j'utilise des shared_ptr. (et sans cela, j'avais une belle fuite m�moire) C'est bien cela ?


    Je devrais �crire plut�t quelque chose comme ceci ?

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
     
    myList.erase(std::remove_if(myList.begin(), myList.end(), [](std::shared_ptr<A> a) { return a->getNbr()%2; } ), myList.end());
    Je regarde et travaille tous les autres points que vous m'avez indiqu� pour poster quelque chose de plus accad�mique

    Encore merci !!

  5. #5
    Membre Expert
    Homme Profil pro
    Ing�nieur d�veloppement logiciels
    Inscrit en
    Juin 2011
    Messages
    760
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, H�rault (Languedoc Roussillon)

    Informations professionnelles :
    Activit� : Ing�nieur d�veloppement logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 760
    Par d�faut
    std::list::remove_if supprime bien les �l�ments. C'est std::remove_if qui les d�place. du list.remove_if(...) ou list.erase(std::remove_if(...), end) font la m�me chose mais la premi�re forme est plus efficace et simple.

  6. #6
    Expert confirm�
    Homme Profil pro
    Ing�nieur d�veloppement mat�riel �lectronique
    Inscrit en
    D�cembre 2015
    Messages
    1 599
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 62
    Localisation : France, Bouches du Rh�ne (Provence Alpes C�te d'Azur)

    Informations professionnelles :
    Activit� : Ing�nieur d�veloppement mat�riel �lectronique
    Secteur : High Tech - �lectronique et micro-�lectronique

    Informations forums :
    Inscription : D�cembre 2015
    Messages : 1 599
    Par d�faut
    Oui, et oui.
    remove_if() utilise des move() pour effectuer des transferts optimis�s vers la fin, il peut laisser des pointeurs vides car apr�s un remove() on s'engage � d�truire les �l�ment d�plac�s. Et je crains que si on supprime un �l�ment d�j� � la fin, m�me si c'est un shared_ptr<> le destructeur ne sera pas appel�. Il faut donc bien ajouter un erase() comme tu l'as fait.

  7. #7
    Membre confirm�
    Profil pro
    Enseignant
    Inscrit en
    Septembre 2011
    Messages
    43
    D�tails du profil
    Informations personnelles :
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activit� : Enseignant

    Informations forums :
    Inscription : Septembre 2011
    Messages : 43
    Par d�faut
    J'essaie de prendre en compte vos remarques et je suis arriv� � ceci:

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
     
    #include <iostream>
    #include <vector>
    #include <memory>
    #include <algorithm>
     
    class A // construite pour l'exemple ...
    {
    public:
    	A(int _nbr, int _valeur){
    		nbr=_nbr; valeur =_valeur;
    		std::cout << "Création de " << nbr << std::endl;
    	}
    	~A(){std::cout << "suppression de " << nbr << std::endl; };
    	int getNbr() {return nbr;}  // pour avoir des fonctions à utiliser
    	int getValue() {return valeur;}  // pour avoir des fonctions à utiliser
    	void setValue(int _v) { valeur = _v;}  // pour avoir des fonctions à utiliser
    private:
    	int nbr;
    	int valeur;
    };
     
     
    int main(int argc, char **argv)
    {
    	std::vector< std::unique_ptr<A> > myVector;
     
    	//creation d'élements du vecteur
    	for(int i=0;i<7; i++)
    		myVector.push_back( std::make_unique<A>(i, 3*i-1) );
     
    	//suppression des éléments impairs
    	myVector.erase(std::remove_if(myVector.begin(), myVector.end(), [](std::unique_ptr<A> &a) { return a->getNbr()%2; } ), myVector.end());
     
    	// affichage du vecteur
    	for(auto const& l : myVector)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//recherche d'un élément particulier i=4
    	auto it = find_if(myVector.begin(), myVector.end(), [](std::unique_ptr<A> &a) { return a->getNbr()==4; } );
    	if (it != myVector.end())
    		(*it)->setValue(-8);
     
    	// affichage du vecteur
    	for(auto const& l : myVector)
    		std::cout << l->getNbr() << " " << l->getValue() << std::endl;
     
    	//suppression totale
    	myVector.clear();
     
    	return 0;
    }
    Est ce que cela semble plus propre ?

+ R�pondre � la discussion
Cette discussion est r�solue.

Discussions similaires

  1. explications sur un petit code
    Par salseropom dans le forum C
    R�ponses: 3
    Dernier message: 27/04/2007, 17h03
  2. Je d�bute -> Conseils sur mon prog (code, lisibilit� etc.)
    Par asxasx dans le forum Interfaces Graphiques en Java
    R�ponses: 5
    Dernier message: 22/03/2007, 08h31
  3. Adaptation du tutoriel sur l'export au format PDF
    Par aquila dans le forum Access
    R�ponses: 5
    Dernier message: 15/02/2007, 14h32
  4. Adapter une image sur un bouton...
    Par Arnaud F. dans le forum Interfaces Graphiques en Java
    R�ponses: 6
    Dernier message: 24/04/2006, 18h33
  5. help sur un petit code avec XMLHttpRequest et setTimeout
    Par grinder59 dans le forum G�n�ral JavaScript
    R�ponses: 4
    Dernier message: 01/10/2005, 10h22

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo