manipulation de std::vector problème de mémoire

manipulation de std::vector problème de mémoire - C++ - Programmation

Marsh Posté le 29-07-2006 à 01:07:47    

Bonjour a tous!
 
Je suis confronte a de serieux problemes avec la manipulation des std::vector en c++ avec Visual .Net 2003. J' ai developpe un algorithme qui doit gerer des listes d objets assez complexes j utilise donc des vector pour les stocker.
 
Jusque la pas trop de probleme mais par la suite j ai tente d integrer mon algorithme a un autre projet que j ai adapte et les methodes communiquent par le biais de std::vector< std::vector<int> > de maniere iterative. Mais mon programme fini par s arreter pour cause de probleme de memoire de ce type:
 
 
Citation:
 
Microsoft C++ exception: std::bad_alloc @ 0x0012ecac.  
 
 
Y a t-il un probleme connu avec le fait d envoyer d envoyer en parametres des pointeurs sur des std::vector et de retourner des objets de type std::vector par le biais de methodes d'objet ou de methode statique.
 
Voici un exemple de code contenue dans une methode appele de facon iterative:
 
 
Code :
        std::vector<int> mvRef;
 int num4x4Blocks = width/4*height/4;
 blocks4x4.reserve(num4x4Blocks);
 mvRef.reserve(2*num4x4Blocks);
       
        //
        //
        // Insertion des valeurs dans mvRef a l'aide de differentes
        // methodes
        //
        //
 
         
        return mvRef;    // Ceci cree une erreur de type memory a la 2 eme
                              // iteration
Notez qu'il suffit de modifier un bout de code pour que l erreur apparaissent dans une autre methode qui a le meme genre de procede
 
 
 
Toutes vos suggestions sont les bienvenues...

Reply

Marsh Posté le 29-07-2006 à 01:07:47   

Reply

Marsh Posté le 02-08-2006 à 22:30:17    

Mouais.... je serai tenté de te conseiller d'acheter une barre de RAM en plus :D
 
Bref, bref... essaye d'optimiser l'espace mémoire:
- utilise: fct(const Classe& param) dès que possible, celà indique de passer un pointeur vers une zone mémoire non-modifiable plutôt que de faire une re-copie,
- essaye: inline Classe fct() pour que le compilo ne soit pas tenté de faire de re-copies inutiles lors de retours de fonctions.

Reply

Marsh Posté le 02-08-2006 à 23:52:40    

Et surtout de laisser tomber les vector et d'utiliser les std:: deque car vector demande de la mémoire contigüe, contrairement à deque (si le pb vient de grosses allocations).
http://www.codeproject.com/vcpp/st [...] _deque.asp
http://www.gotw.ca/gotw/054.htm


Message édité par el muchacho le 03-08-2006 à 00:00:54

---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 03-08-2006 à 14:29:38    

passe ton vecteur par référence, ça évite une recopie potentielle (qui peut être supprimmée par le NRVO).
 
je ne sais quelle tête a ton code entre les //
 
si tu utilises reserve(), tu dois continuer a utiliser push_back()
si tu veux utiliser [] tu dois utiliser resize()

Reply

Marsh Posté le 03-08-2006 à 18:54:52    

Finalement je me suis resigne a utilier un tableau de pointeurs a la place des vecteurs car meme n utilisant que du referencement ( c est a dire en ne transmettant jamais une copie d un objet envoye en parametre a une methode mais plutot la reference de ce dernier)  et ca plante moins facilement. Mais comme mon programme est engage dans un boucle qui devrais selon les cas atteindre jusqu a un maximum de 1000 iterations environ, Je fini tout de meme par avoir un runtime error et mon programme se voit forcer d etre interrompu par le system. Pourtant ma contribution n est qu un plug in a un soft qui tourne deja sans aucun probleme meme avec plus de 1000 iteration. Je sais que la coquille vient de mon bout de code mais ou exactement? aucune idee. Je crois avoir tout essaye. Cependant j ai remarque un phenomene bizarre: lorsque la reference a **blocks est envoye en paremetre (&blocks) a une methode qui ne fait que de lire les valeurs pointee sans en modifier aucune elles sont alteree des la fin de l execution de la methode. D ou peut venir ce genre de phenomenes en general?

Reply

Marsh Posté le 03-08-2006 à 18:58:56    

Pourtant je veille a utiliser les des delete apres des appels a new et des delete [] pour new []. Mais souvent une erreur se produit m indiquant que la desallocation n est pas possible car l objet est NULL!!!!  
 
Je vais essayer de voir ce qu'offre la solution std::deque pour essayer de sortir de ce petrin

Reply

Marsh Posté le 03-08-2006 à 19:35:03    

utilises les smart pointers de boost.
 
essayes de structurer ton code de manière a avoir:
 
début
-> alloc / creation objet
 
boucle de traitement
    -> modif sans realloc si possible
 
fin
->desalloc (automatique par RAII / smart_ptr)
 
quand je vois ton bout de code qui retourne un std::vector j'ai peur que ton plug-in soit mal structuré avec des création / copie / destruction (buggées) inutiles.

Reply

Marsh Posté le 03-08-2006 à 21:46:17    

Les smart_ptr sont compatibles avec les conteneurs STL ? Parce qu'il me semble que ce n'est pas le cas avec les auto_ptr.
 
Sinon +1 pour la structuration. J'ai bien peur que les deque n'arrangent rien la-dedans. Une gestion rigoureuse et symétrique des allocs/destructions, me parait plus appropriée, accès aux éléments par itérateurs, etc.
 
http://new-brunswick.net/workshop/ [...] #faq-16.19


Message édité par el muchacho le 03-08-2006 à 22:29:57

---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 03-08-2006 à 21:50:14    

ceux de boost oui.

Reply

Marsh Posté le 03-08-2006 à 23:25:59    

vector sans les copies inutiles en appel et retour de fonction

Reply

Marsh Posté le 03-08-2006 à 23:25:59   

Reply

Marsh Posté le 03-08-2006 à 23:28:00    

bjone a écrit :

ceux de boost oui.


 
pas tous, pas les noncopyable, enfin faut voir les contraintes pour le type contenu, et dans boost il y a aussi les "pointer contener"

Reply

Marsh Posté le 03-08-2006 à 23:37:19    

heu ouais exact :D (enfin c'était dans l'esprit y'a des chances de trouver ce qu'il te faut)

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed