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

VB.NET Discussion :

Limite de taille List(Of ) - System.OutOfMemoryException


Sujet :

VB.NET

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre chevronné Avatar de electroremy
    Homme Profil pro
    Ingénieur sécurité
    Inscrit en
    Juin 2007
    Messages
    999
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Doubs (Franche Comté)

    Informations professionnelles :
    Activité : Ingénieur sécurité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2007
    Messages : 999
    Par défaut Limite de taille List(Of ) - System.OutOfMemoryException
    Bonjour à tous,

    J'ai un programme qui stocke pas mal de données en RAM

    Je tombe sur cette erreur :

    System.OutOfMemoryException: Les dimensions du tableau dépassent la plage prise en charge.
    à System.Collections.Generic.List`1.set_Capacity(Int32 value)
    à System.Collections.Generic.List`1.EnsureCapacity(Int32 min)
    à System.Collections.Generic.List`1.Add(T item)

    Je stocke mes données dans
    - deux List(Of Single)
    - une List(Of Color)

    C'est un programme qui fait de la 3D.

    J'arrive à gérer 22 millions de triangles, pour chaque triangle on stoke :
    - trois nombres Single pour le vecteur normal
    - neuf nombre Single pour les coordonnées (X,Y,Z) des trois sommets
    - une couleur (entier 32 bits)
    Cela fait 1,06 Go de données utiles (un single étant stocké sur 4 octets), auxquelles il faut ajouter les octets requis par les pointeurs utilisés par les listes

    Au delà (25 millions de triangles) ça plante.

    Alors oui 22 millions de triangles c'est déjà pas mal
    Avec ces données, le programme compilé en release 64 bits, sous Seven 64 bits intégrale, consomme 1,9 à 2,6Go de RAM.
    (NB : en plus les triangles sont envoyés dans la carte graphique via Open GL pour affichage, tout en restant en RAM pour les calculs de mon programme)

    Je n'ai pas à rougir, VisCamView n'arrive pas à ouvrir ce fichier STL de 22 millions de triangles, et MeshLab y arrive mais en chie

    Mon PC a 16 Go de RAM, lorsque le plantage se produit il n'y a même pas la moitié de ces 16 Go qui est utilisée... C'est frustrant...
    Je programme aussi en embarqué (microcontrôleur), je suis habitué à pouvoir exploiter le hardware à 100% j'aimerais bien exploiter mon PC à fond

    Est-il possible d'aller au dela ?

    Il me semble que l'intérêt du 64 bits par rapport au 32 bits est justement la possibilité d'outrepasser la limite de 4Go de RAM

    Et vis à vis de la fragmentions de la mémoire, il me semble que c'était aussi l'intérêt des listes par rapport au tableaux

    A bientôt

  2. #2
    Expert éminent Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 197
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 197
    Par défaut
    une appli .net peut prendre plusieurs Go de ram, je l'ai déjà vu avec des fuites mémoires

    il me semble qu'outofmemory peut arriver lorsque l'allocation de ram est trop rapide

    un list est un array en plus pratique, mais il y a bien un array dedans
    un array n'est pas redimensionnable sans refaire une copie de l'existant dans un tableau plus grand
    pour ca le list dimensionne son tableau au démarrage à une taille donnée, puis quand un .add fait que ca devrait dépasser il créé un array 2x plus grand puis recopie le 1er dans le 2eme
    ceci a un cout en mémoire et en performance, si tu sais vaguement combien va faire ton list à l'avance tu peux faire en sorte qu'il dimensionne l'array via la surcharge du constructeur new list<machin>(int capacity)
    idéalement à une taille qu'il ne dépassera pas ce qui évitera toute recopie inutile

    si ca ne corrige pas le problème essaye d'allouer un peu moins vite les choses, ne serait ce que pour voir si c'est bien la vitesse de remplissage le problème (ce n'est pas forcément une solution idéale)

    sinon il y a des méthodes dans le framework pour prévenir qu'on va allouer beaucoup de ram (et pour la rendre plus tard), je l'ai plus en tête mais ca permettrait peut etre d'éviter l'out of memory
    Cours complets, tutos et autres FAQ ici : C# - VB.NET

  3. #3
    Membre émérite
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Octobre 2006
    Messages
    727
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Jura (Franche Comté)

    Informations professionnelles :
    Activité : Responsable de service informatique
    Secteur : Distribution

    Informations forums :
    Inscription : Octobre 2006
    Messages : 727
    Par défaut
    Bonjour,

    Ce n'est pas le nombre d'éléments qui est en cause, c'est certain, la limite comme indiqué dans l'erreur, est d''environ 2 milliards (Int32).
    Y a t'il une limite en taille globale du même acabit, genre un pointeur Int32 qui est chargé de pointer dans la List et qui lui se trouve dépassé ? Il me semble que Microsoft avait une limite à 2Go pour les objets, et c'est peut être là qu'il faut chercher.
    Un test simple avec une List de quelques centaines ou milliers d'éléments mais de grande taille devrait donner la réponse.

  4. #4
    Membre chevronné Avatar de electroremy
    Homme Profil pro
    Ingénieur sécurité
    Inscrit en
    Juin 2007
    Messages
    999
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Doubs (Franche Comté)

    Informations professionnelles :
    Activité : Ingénieur sécurité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2007
    Messages : 999
    Par défaut
    Merci pour vos réponses.

    Comme c'est pour de la 3D (CAO), le programme est optimisé pour être rapide.

    Les 22 millions de triangles sont créés en 25 secondes par une procédure de génération de forme.

    Si derrière les List(Of ) se cachent des tableaux redimenssionés, il faut créer des tableaux cela me semble évident...
    Le soucis est de savoir quelle taille prendre, dommage de bouffer de la RAM pour créer de petites pièces.
    Ou alors à un moment donné il faudra supprimer les tableaux pour les recréer en plus grand.
    Il n'est pas toujours possible de savoir à l'avance quels quantité de données sera créé.

    Autre aspect des choses : j'ai une liste pour les valeurs NX, NY, NZ et une autre pour les valeurs X1, Y1, Z1... Z3
    Ca serait plus pertinent de prendre une liste NX, une liste NY... une liste Z3 ? Chaque liste serait plus petite

    Autre idée : avoir une liste de liste.
    Chaque fonction qui génère des triangles créé une liste, chaque petite liste est ajoutée dans la liste de liste.
    Le soucis étant que j'ai une fonction "gourmande" qui a elle seule est capable de générer 22 millions de triangles voire plus
    Il faudrait faire une liste NX, une liste NY... une liste Z3 par fonction, et une liste de liste NX... une liste de liste Z3

    Dernière idée : avoir des listes de liste, avec création d'une nouvelle sous-liste de taille fixe une fois une certaine taille limite atteinte.
    Genre je commence avec une liste de taille fixe pour 100.000 triangles; une fois qu'elle est remplie j'en créé une deuxième, et ainsi de suite
    Cela permet d'allouer/libérer la mémoire par bloc de 100.000 triangles, c'est moins violent pour la gestion de la mémoire, et ça permet au programme de ne pas gâcher de la mémoire en allouer une trop grande quantité de mémoire au démarrage. Dans mon code, au moment de la libération, il faudra que j'appelle le garbage collector avant de créer de nouvelles listes.
    Je peux carrément utiliser des tableaux de 100.000 à la place des listes, et avoir une liste de tableaux.
    La bonne nouvelle c'est que je n'ai pas besoin de supprimer les triangles au milieu de la liste, donc c'est gérable avec des tableaux.
    Qu'en pensez vous ?


    A bientôt

  5. #5
    Expert éminent Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 197
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 197
    Par défaut
    j'en pense qu'en effet il y a plusieurs choses à tester pour chercher le plus performant, mais qu'il faudrait déjà que tu règles ton problème d'out of memory exception avant d'avancer, car tant que tu ne sais pas pourquoi il est là tu risques de retomber dessus plus tard

    tu peux tenter ca dans un premier temps : gcAllowVeryLargeObjects element - .NET Framework | Microsoft Docs
    Cours complets, tutos et autres FAQ ici : C# - VB.NET

  6. #6
    Membre chevronné Avatar de electroremy
    Homme Profil pro
    Ingénieur sécurité
    Inscrit en
    Juin 2007
    Messages
    999
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Doubs (Franche Comté)

    Informations professionnelles :
    Activité : Ingénieur sécurité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2007
    Messages : 999
    Par défaut
    Merci

    Ton lien est intéressant mais est limité au 64 bits
    Je voulais que mon programme puisse tourner en 32 bits aussi ; en CAO / FAO on peut dédier un ordinateur un peu ancien pour une machine.

    Comme expliqué j'ai des choses à tester, je pense que mon idée de faire une liste de tableau fixes de 100.000 peut marcher et qu'elle risque même d'apporter un gain en vitesse. C'est chouette il y a deux choses à gagner : outrepasser la limite de mémoire et gagner un peu de vitesse

    Je reviens vers vous quand j'aurais le résultat

    A bientôt

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Comment limiter la taille d'une liste ?
    Par selmagsi dans le forum Général Python
    Réponses: 12
    Dernier message: 13/12/2018, 20h04
  2. [ Eclipse2.1 ][ Plugin ] limiter la taille des boutons
    Par whilecoyote dans le forum Eclipse Java
    Réponses: 1
    Dernier message: 03/11/2005, 16h08
  3. Taille : liste déroulante
    Par souska dans le forum Access
    Réponses: 2
    Dernier message: 20/09/2005, 23h42
  4. [Tomcat][Jsp][Upload]Limiter la taille d'un upload...
    Par Titom dans le forum Servlets/JSP
    Réponses: 4
    Dernier message: 23/05/2005, 15h33
  5. Limiter les 30dernière liste de données?
    Par SkyDev dans le forum Langage SQL
    Réponses: 11
    Dernier message: 08/03/2004, 17h01

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