Question à propose des maps / fragmentation mémoire
4 réponses
Gégé
Bonjour,
J'ai observ=E9 qu'apr=E8s destruction de ma map (qui =E0 un string associe
un vecteur de strings), il reste toujours quelques Mo en m=E9moire (ici
2Mo). Le probl=E8me est mon ex=E9cution devient de plus en plus longue
(sur certaines machines, mais pas sur toutes, environ 10% de plus,
puis 12%, etc.). Je ne connais pas du tout les m=E9canismes d'allocation
m=E9moire sous-jacents, mais je me dis que je rencontre peut etre un
ph=E9nom=E8ne de fragmentation.
Questions :
1- est-il possible apr=E8s destruction de la map de vraiment lib=E9rer la
m=E9moire (en changeant d'allocator ??)
2- avez vous un avis sur ce ph=E9nom=E8ne d'ex=E9cution de plus en plus
long.
Cette action est irreversible, confirmez la suppression du commentaire ?
Signaler le commentaire
Veuillez sélectionner un problème
Nudité
Violence
Harcèlement
Fraude
Vente illégale
Discours haineux
Terrorisme
Autre
Pascal J. Bourguignon
Gégé writes:
J'ai observé qu'après destruction de ma map (qui à un string associe un vecteur de strings), il reste toujours quelques Mo en mémoire (ici 2Mo). Le problème est mon exécution devient de plus en plus longue (sur certaines machines, mais pas sur toutes, environ 10% de plus, puis 12%, etc.). Je ne connais pas du tout les mécanismes d'allocation mémoire sous-jacents, mais je me dis que je rencontre peut etre un phénomène de fragmentation.
Questions : 1- est-il possible après destruction de la map de vraiment libérer la mémoire (en changeant d'allocator ??)
Oui, mais ça n'a aucun intérêt. Pourquoi libères tu la mémoire, si ce n'est pour la réutiliser? Dans ce cas, il vaut mieux ne pas perdre son temps à rendre la mémoire au système, pour la lui redemander immédiatement. D'un autre côté, sur un système comme unix si on a alloué de la mémoire virtuelle qu'on n'utilise pas, elle fini par être paginée dans le swap, et ne pose pas de problème (dans des limites normales).
2- avez vous un avis sur ce phénomène d'exécution de plus en plus long.
Oui. C ou C++ est plus lent qu'un langage comme Lisp qui a un bon ramasse-miette, à cause des algorithmes utilisés par malloc et free (new et delete).
Mon conseille serait d'utiliser un bon ramasse miette, mais c'est difficile avec des langages comme C et C++. BoehmGC peut aider, mais il ne peut pas être aussi bon qu'il le faudrait (ce n'est pas un ramasse miette générationnel déplaçant les objets).
-- __Pascal Bourguignon__ http://www.informatimago.com/ A bad day in () is better than a good day in {}.
Gégé <valasg@gmail.com> writes:
J'ai observé qu'après destruction de ma map (qui à un string associe
un vecteur de strings), il reste toujours quelques Mo en mémoire (ici
2Mo). Le problème est mon exécution devient de plus en plus longue
(sur certaines machines, mais pas sur toutes, environ 10% de plus,
puis 12%, etc.). Je ne connais pas du tout les mécanismes d'allocation
mémoire sous-jacents, mais je me dis que je rencontre peut etre un
phénomène de fragmentation.
Questions :
1- est-il possible après destruction de la map de vraiment libérer la
mémoire (en changeant d'allocator ??)
Oui, mais ça n'a aucun intérêt. Pourquoi libères tu la mémoire, si ce
n'est pour la réutiliser? Dans ce cas, il vaut mieux ne pas perdre son
temps à rendre la mémoire au système, pour la lui redemander
immédiatement. D'un autre côté, sur un système comme unix si on a alloué
de la mémoire virtuelle qu'on n'utilise pas, elle fini par être paginée
dans le swap, et ne pose pas de problème (dans des limites normales).
2- avez vous un avis sur ce phénomène d'exécution de plus en plus
long.
Oui. C ou C++ est plus lent qu'un langage comme Lisp qui a un bon
ramasse-miette, à cause des algorithmes utilisés par malloc et free (new
et delete).
Mon conseille serait d'utiliser un bon ramasse miette, mais c'est
difficile avec des langages comme C et C++. BoehmGC peut aider, mais il
ne peut pas être aussi bon qu'il le faudrait (ce n'est pas un ramasse
miette générationnel déplaçant les objets).
--
__Pascal Bourguignon__ http://www.informatimago.com/
A bad day in () is better than a good day in {}.
J'ai observé qu'après destruction de ma map (qui à un string associe un vecteur de strings), il reste toujours quelques Mo en mémoire (ici 2Mo). Le problème est mon exécution devient de plus en plus longue (sur certaines machines, mais pas sur toutes, environ 10% de plus, puis 12%, etc.). Je ne connais pas du tout les mécanismes d'allocation mémoire sous-jacents, mais je me dis que je rencontre peut etre un phénomène de fragmentation.
Questions : 1- est-il possible après destruction de la map de vraiment libérer la mémoire (en changeant d'allocator ??)
Oui, mais ça n'a aucun intérêt. Pourquoi libères tu la mémoire, si ce n'est pour la réutiliser? Dans ce cas, il vaut mieux ne pas perdre son temps à rendre la mémoire au système, pour la lui redemander immédiatement. D'un autre côté, sur un système comme unix si on a alloué de la mémoire virtuelle qu'on n'utilise pas, elle fini par être paginée dans le swap, et ne pose pas de problème (dans des limites normales).
2- avez vous un avis sur ce phénomène d'exécution de plus en plus long.
Oui. C ou C++ est plus lent qu'un langage comme Lisp qui a un bon ramasse-miette, à cause des algorithmes utilisés par malloc et free (new et delete).
Mon conseille serait d'utiliser un bon ramasse miette, mais c'est difficile avec des langages comme C et C++. BoehmGC peut aider, mais il ne peut pas être aussi bon qu'il le faudrait (ce n'est pas un ramasse miette générationnel déplaçant les objets).
-- __Pascal Bourguignon__ http://www.informatimago.com/ A bad day in () is better than a good day in {}.
Gégé
Hello,
Merci pour ces éléments. La réponse à ma première question semble assez cohérente. Si j'attends un bon moment, genre 5/6 minutes, la mémoire se vide d'un coup ...
Sur le 2è point, je ne suis pas du tout familier avec ces mécanismes, il va falloir que j'approfondisse. En revanche, n'est-il pas étrange que le phénomène ne se constate pas sur tous les PC ? qualité de RAM ?
Merci bcp
Hello,
Merci pour ces éléments.
La réponse à ma première question semble assez cohérente.
Si j'attends un bon moment, genre 5/6 minutes, la mémoire se vide d'un
coup ...
Sur le 2è point, je ne suis pas du tout familier avec ces mécanismes,
il va falloir que j'approfondisse.
En revanche, n'est-il pas étrange que le phénomène ne se constate pas
sur tous les PC ? qualité de RAM ?
Merci pour ces éléments. La réponse à ma première question semble assez cohérente. Si j'attends un bon moment, genre 5/6 minutes, la mémoire se vide d'un coup ...
Sur le 2è point, je ne suis pas du tout familier avec ces mécanismes, il va falloir que j'approfondisse. En revanche, n'est-il pas étrange que le phénomène ne se constate pas sur tous les PC ? qualité de RAM ?
Merci bcp
Gégé
Autre petit question : est-ce que changer l'allocator de la map peut aider ?
Autre petit question : est-ce que changer l'allocator de la map peut
aider ?
Autre petit question : est-ce que changer l'allocator de la map peut aider ?
Pascal J. Bourguignon
Gégé writes:
Autre petit question : est-ce que changer l'allocator de la map peut aider ?
Ça peut faciliter le retour de la mémoire au système, mais en général, ce n'est pas conseiller de perdre son temps à le faire.
Encore une fois, si tu libère la mémoire c'est soit parce que tu as fini le travail et alors, déjà ce n'était pas la peine de la libérée puisque le processus va être tué, soit parce que tu vas faire autre chose, utilisant la mémoire, et donc il vaut mieux utiliser cette mémoire déjà obtenue du système, plutôt que de la rendre au système pour la lui redemander immédiatement.
Une façon simple de demander et de rendre la mémoire au système, c'est d'utiliser mmap(2). Dans le cas normal de sbrk(2), la mémoire ne peut être rendue que dans la mesure où il n'y a pas de bloc alloué au delà. Dans le cas de mmap(2) chaque bloc alloué peut être rendu indépendament. Donc on peut s'ammuser à écrire un allocateur pour std::map auquel on fourni de la mémoire avec mmap(2), et que l'on peut rendre lorsqu'on supprime la std::map. Mais je répète, ça va prendre du temps (deux appels systèmes) pour rien.
-- __Pascal Bourguignon__ http://www.informatimago.com/ A bad day in () is better than a good day in {}.
Gégé <valasg@gmail.com> writes:
Autre petit question : est-ce que changer l'allocator de la map peut
aider ?
Ça peut faciliter le retour de la mémoire au système, mais en général,
ce n'est pas conseiller de perdre son temps à le faire.
Encore une fois, si tu libère la mémoire c'est soit parce que tu as fini
le travail et alors, déjà ce n'était pas la peine de la libérée puisque
le processus va être tué, soit parce que tu vas faire autre chose,
utilisant la mémoire, et donc il vaut mieux utiliser cette mémoire déjà
obtenue du système, plutôt que de la rendre au système pour la lui
redemander immédiatement.
Une façon simple de demander et de rendre la mémoire au système, c'est
d'utiliser mmap(2). Dans le cas normal de sbrk(2), la mémoire ne peut
être rendue que dans la mesure où il n'y a pas de bloc alloué au delà.
Dans le cas de mmap(2) chaque bloc alloué peut être rendu indépendament.
Donc on peut s'ammuser à écrire un allocateur pour std::map auquel on
fourni de la mémoire avec mmap(2), et que l'on peut rendre lorsqu'on
supprime la std::map. Mais je répète, ça va prendre du temps (deux
appels systèmes) pour rien.
--
__Pascal Bourguignon__ http://www.informatimago.com/
A bad day in () is better than a good day in {}.
Autre petit question : est-ce que changer l'allocator de la map peut aider ?
Ça peut faciliter le retour de la mémoire au système, mais en général, ce n'est pas conseiller de perdre son temps à le faire.
Encore une fois, si tu libère la mémoire c'est soit parce que tu as fini le travail et alors, déjà ce n'était pas la peine de la libérée puisque le processus va être tué, soit parce que tu vas faire autre chose, utilisant la mémoire, et donc il vaut mieux utiliser cette mémoire déjà obtenue du système, plutôt que de la rendre au système pour la lui redemander immédiatement.
Une façon simple de demander et de rendre la mémoire au système, c'est d'utiliser mmap(2). Dans le cas normal de sbrk(2), la mémoire ne peut être rendue que dans la mesure où il n'y a pas de bloc alloué au delà. Dans le cas de mmap(2) chaque bloc alloué peut être rendu indépendament. Donc on peut s'ammuser à écrire un allocateur pour std::map auquel on fourni de la mémoire avec mmap(2), et que l'on peut rendre lorsqu'on supprime la std::map. Mais je répète, ça va prendre du temps (deux appels systèmes) pour rien.
-- __Pascal Bourguignon__ http://www.informatimago.com/ A bad day in () is better than a good day in {}.