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 :

operateur éviter copie


Sujet :

C++

  1. #1
    Membre habitué
    Profil pro
    Inscrit en
    Juin 2013
    Messages
    294
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2013
    Messages : 294
    Points : 128
    Points
    128
    Par défaut operateur éviter copie
    Bonjour,

    J'ai l'opérateur suivant. Mon problème est que mon code tourne très lentement.
    Je penses que cela est due au fait que je créé un vecteur à chaque utilisation de *.
    Mais je ne vois pas comment on peut l'éviter.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    vecteur tridiag::operator*(const vecteur V){
    		int N=V.size();
    		vecteur Y(N);
     
    		Y(0) = ann[0]*V(0) + a1n[0]*V(1);
    		for (int i=1; i<N-1; ++i)
    			Y(i) = an1[i-1]*V(i-1)+ann[i]*V(i)+a1n[i]*V(i+1);
     
    		Y(N-1) = an1[N-2]*V(N-2)+ann[N-1]*V(N-1);
    		return Y;
    	}
    Merci d'avance.

  2. #2
    Expert confirmé
    Homme Profil pro
    Étudiant
    Inscrit en
    Juin 2012
    Messages
    1 711
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juin 2012
    Messages : 1 711
    Points : 4 442
    Points
    4 442
    Par défaut
    Citation Envoyé par xavierdestev Voir le message
    Je penses que cela est due au fait que je créé un vecteur à chaque utilisation de *.
    La seule façon d'en être sur est le profiling.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    vecteur tridiag::operator*(const vecteur V) {
    Il y à ici une copie inutile, tu peux passer une ref en paramètre.

    Tu peux aussi éviter la création d'un nouveau vecteur, si tu en possède déja un (si possible à la bonne taille)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    void dot(const vecteur& V, vecteur& result) {
        int N=V.size();
        if(result.size() != N) {
           result.resize(N);
        }
        result(0) = ...;
        ...
    }

  3. #3
    Membre habitué
    Profil pro
    Inscrit en
    Juin 2013
    Messages
    294
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2013
    Messages : 294
    Points : 128
    Points
    128
    Par défaut
    Merci pour ta réponse.
    Il y à ici une copie inutile, tu peux passer une ref en paramètre.

    --->Si je fais cela j'obtiens, cpp/vecteur.cpp:57:17: attention : reference to local variable ‘U’ returned

    Tu peux aussi éviter la création d'un nouveau vecteur, si tu en possède déja un (si possible à la bonne taille)

    -->Je préfères éviter d'avoir recours à une méthode plutot qu'à la surdéfinition d'un opérateur.

  4. #4
    Expert confirmé
    Homme Profil pro
    Étudiant
    Inscrit en
    Juin 2012
    Messages
    1 711
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juin 2012
    Messages : 1 711
    Points : 4 442
    Points
    4 442
    Par défaut
    Citation Envoyé par xavierdestev Voir le message
    cpp/vecteur.cpp:57:17: attention : reference to local variable ‘U’ returned
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    vecteur tridiag::operator*(const vecteur& V){
    	int N=V.size();
    	vecteur Y(N);
     
    	Y(0) = ann[0]*V(0) + a1n[0]*V(1);
    	for (int i=1; i<N-1; ++i)
    		Y(i) = an1[i-1]*V(i-1)+ann[i]*V(i)+a1n[i]*V(i+1);
     
    	Y(N-1) = an1[N-2]*V(N-2)+ann[N-1]*V(N-1);
    	return Y;
    }
    Le paramètre qui est passé par référence, pas la valeur de retour.

  5. #5
    Expert éminent sénior
    Avatar de Luc Hermitte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2003
    Messages
    5 275
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2003
    Messages : 5 275
    Points : 10 985
    Points
    10 985
    Par défaut
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    vecteur tridiag::operator*(vecteur const& V) const{
            assert(! V.empty());
    	vecteur Y(V.size()); // je tenterai en premier. Dans mes souvenirs, il y a ainsi plus de chances de permettre une copy-elision
    	const size_t N=V.size() -1; // const n'est pas une optim; mais le -1 peut l'être
     
     	Y(0) = ann[0]*V(0) + a1n[0]*V(1);
    	for (size_t i=1; i<N; ++i)
    		Y(i) = an1[i-1]*V(i-1)+ann[i]*V(i)+a1n[i]*V(i+1);
     
    	Y(N) = an1[N-1]*V(N-2)+ann[N]*V(N);
    	return Y;
    }
    Prendre le vecteur de retour par référence ne vaut le coup que si la fonction est appelée de multiples fois avec la même variable en paramètre.
    Il faut faire confiance au compilo sinon pour profiter de l'élision de copie et des rvalue-reférences sinon -- penser à écrire un constructeur de déplacement dans la classe vecteur.

    Après, il est toujours possible de passer d'une notation indices à l'arithmétique de pointeurs : 1- si le profiling dit bien que le temps est perdu dans la fonction et 2- si le compilo est plus efficace avec cette technique plutôt que l'autre -- des fois ça change.
    Blog|FAQ C++|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS|Bons livres sur le C++
    Les MP ne sont pas une hotline. Je ne réponds à aucune question technique par le biais de ce média. Et de toutes façons, ma BAL sur dvpz est pleine...

Discussions similaires

  1. Copie de vector avec operateur =
    Par LinuxUser dans le forum C++
    Réponses: 13
    Dernier message: 25/08/2014, 14h40
  2. zip.h : éviter la copie d'un fichier
    Par troumad dans le forum C
    Réponses: 0
    Dernier message: 20/02/2012, 11h23
  3. Réponses: 6
    Dernier message: 12/07/2007, 18h18
  4. Constructeur par copie et operateurs
    Par NiamorH dans le forum C++
    Réponses: 11
    Dernier message: 07/07/2007, 17h37

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