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

Lazarus Pascal Discussion :

Longueur d'une AnsiString


Sujet :

Lazarus Pascal

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Expert confirmé
    Avatar de Jipété
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    11 128
    Détails du profil
    Informations personnelles :
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations forums :
    Inscription : Juillet 2006
    Messages : 11 128
    Par défaut Longueur d'une AnsiString
    Bonjour à tous,

    Dans la doc trouvée là, je peux lire :
    Ansistrings are strings that have no length limit.
    Sauf que, j'ai créé un tout petit bazar pour mettre en évidence que je ne peux pas monter à 1,4 Go --> erreur "out of memory" (1,3 ça passe, je n'ai pas creusé pour trouver exactement où ça coince) :
    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
    var
      ln: int64 = 1000000000; // 1 Go
     
    procedure TMainForm.ButtonTestClick(Sender: TObject);
    var
      s: ansistring;
    begin
      SetLength(s, ln);
      ShowMessage(IntToStr(Length(s)));
      SetLength(s, 10); // pour libérer
    end;
     
    procedure TMainForm.ButtonPlusClick(Sender: TObject);
    begin
      ln := ln + 100000000; // + 100 Mo
    end;
     
    procedure TMainForm.ButtonMoinsClick(Sender: TObject);
    begin
      ln := ln - 100000000; // - 100 Mo
    end;
    Lorsque le ShowMessage affiche 1,3 Go, le "moniteur de ressources" de 7 me dit que la mémoire utilisée par le processus est de 997 Mo (ça descend doucement), et la mémoire disponible de 958 Mo (et ça monte doucement).

    Une idée pour pouvoir avoir une Ansistring de 5 ou 6 Go ?

    Bonne journée,

  2. #2
    Rédacteur/Modérateur
    Avatar de M.Dlb
    Inscrit en
    Avril 2002
    Messages
    2 466
    Détails du profil
    Informations personnelles :
    Âge : 40

    Informations forums :
    Inscription : Avril 2002
    Messages : 2 466
    Par défaut
    Citation Envoyé par Jipété Voir le message
    Une idée pour pouvoir avoir une Ansistring de 5 ou 6 Go ?
    Euh quelle est l'utilité ? Ou plutôt qu'est-ce que tu veux faire ? Il y a surement une autre façon de faire ce que tu souhaites...

  3. #3
    Expert confirmé
    Avatar de Jipété
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    11 128
    Détails du profil
    Informations personnelles :
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations forums :
    Inscription : Juillet 2006
    Messages : 11 128
    Par défaut
    Yop !
    Citation Envoyé par wormful_sickfoot Voir le message
    Euh quelle est l'utilité ? Ou plutôt qu'est-ce que tu veux faire ?
    Et bien, je veux extraire des fichiers depuis un .zip. Je me suis inspiré de ça, trouvé dans "Zippit.pas" :
    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
    procedure TZippit.AddFile(const Name: String);
    var
      F: TFileStream;
      B: String;
    begin
      F := TFileStream.Create(Name, fmOpenRead);
      try
        SetLength(B, F.Size);
        F.ReadBuffer(B[1], F.Size);
        inherited AddFile(Name, 0);
        Data[Count-1] := B;
      finally
        F.Free;
      end;
    end;
    pour écrire ça :
    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
    procedure TZippit.ExtractFile(const i: integer; const Name: String;
      const l: int64);
    var
      F: TFileStream;
      B: AnsiString;
    begin
      F := TFileStream.Create(Name, fmCreate);
      try
        SetLength(B, l); // run error 203 si gros fichiers :-( mais ok sur petits... 
        B := Uncompressed[i]; // dans SciZipFile.pas, qui tape ensuite dans dzlib.pas
        F.WriteBuffer(Pointer(B)^, l);
      finally
        F.Free;
      end;
    end;
    Citation Envoyé par wormful_sickfoot Voir le message
    Il y a surement une autre façon de faire ce que tu souhaites...
    Je m'en doute un peu (faire le boulot blocks par blocks, style 1 Mo à la fois), mais je vais misérer grave, je sens...

    Ah, je précise que mes fichiers .zip d'origine sont créés avec 7z, car en regardant le code de AddFile ci-dessus, je me dis que je ne pourrai jamais zipper des gros fichiers, le problème d'allocation mémoire serait le même

  4. #4
    Expert confirmé

    Inscrit en
    Août 2006
    Messages
    3 967
    Détails du profil
    Informations forums :
    Inscription : Août 2006
    Messages : 3 967
    Par défaut
    Qia,

    Je pense que tu prends un mauvais chemin, ne serait-ce que parce que tu te heurteras forcément à la limite de mémoire disponible, quelle que soit la quantité installée (il suffira pour ça que tu veuilles gérer de plus gros fichiers).

  5. #5
    Membre éprouvé

    Homme Profil pro
    Développeur informatique
    Inscrit en
    Décembre 2006
    Messages
    58
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Décembre 2006
    Messages : 58
    Par défaut
    alors comment ça marche une ansistring

    c'est une sorte de buffer en mémoire dont la taille n'est pas accessible directement (à moins de pointer qq octets avant le début) et qui est alloué à la volée quand on fait une assignation ou un setlength. De plus, il faut savoir que quand on fait change la longueur, le gestionnaire de mémoire alloue la nouvelle taille demandée, copie le contenu de l'ancienne zone dans la nouvelle et efface l'ancienne.

    La taille mémoire d'un poste n'est pas extensible à l'infini, de plus il faut laisser de la place pour les autres. D'où il ressort :
    - travaille en boucle,
    - trouve une taille de buffer intermédiaire que tu ne changerad pas toutes les 3ms (car oui copier des blocs mémoire ça prend du temps) (1Mo c'est bien)


    PS 1ko=1024 octets donc 1Go ce n'est pas 1000000000 octets dans le monde des programmeurs (ce que tu utilises, c’est la notation des marchands de disque dur qui nous enfument mais ceci est un autre sujet)

  6. #6
    Expert confirmé
    Avatar de Jipété
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    11 128
    Détails du profil
    Informations personnelles :
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations forums :
    Inscription : Juillet 2006
    Messages : 11 128
    Par défaut
    Re,
    Citation Envoyé par mtournay Voir le message
    (...)D'où il ressort :
    - travaille en boucle,
    - trouve une taille de buffer intermédiaire que tu ne changerad pas toutes les 3ms (car oui copier des blocs mémoire ça prend du temps) (1Mo c'est bien)
    Oui, je me doutais bien de tout ça, je voulais juste me l'entendre confirmer...
    Je vais donc envisager un buffer intermédiaire, mais comment ça va se passer au niveau de la décompression ?
    Si j'envoie un buffer de 1 Mo de données et que le système de décompression a besoin de données qui sont après ce 1 Mo ? (je ne sais pas trop comment fonctionne le système de décompression...)
    Bref, je suis pas rendu, à moins que quelqu'un ait déjà joué avec tout ça (Lazarus ou Delphi) pour me mettre sur la voie...

    Citation Envoyé par mtournay Voir le message
    PS 1ko=1024 octets donc 1Go ce n'est pas 1000000000 octets dans le monde des programmeurs (ce que tu utilises, c’est la notation des marchands de disque dur qui nous enfument mais ceci est un autre sujet)
    Yes, I know, mais c'était pour faire simple,

    Bon week-end,

  7. #7
    Expert confirmé

    Inscrit en
    Août 2006
    Messages
    3 967
    Détails du profil
    Informations forums :
    Inscription : Août 2006
    Messages : 3 967
    Par défaut
    Mau,
    Citation Envoyé par mtournay Voir le message
    PS 1ko=1024 octets donc 1Go ce n'est pas 1000000000 octets dans le monde des programmeurs (ce que tu utilises, c’est la notation des marchands de disque dur qui nous enfument mais ceci est un autre sujet)
    Mais si !

    Pour parler de Ko, Mo, Go ... au sens habituel des informaticiens, la norme est d'écrire Kio, Mio, Gio ..., justement pour lever l'ambiguïté créée par nos habitudes.

    Mais dans le contexte, je crois que la valeur désirée devrait effectivement être en Gio, donc 1024*1024*1024 = 1*073*741*824

Discussions similaires

  1. Longueur d'une extension > 3 caractères
    Par Rodrigue dans le forum Windows
    Réponses: 5
    Dernier message: 10/06/2005, 19h58
  2. [langage] longueur d'une chaine lue ds un fichier
    Par perlaud dans le forum Langage
    Réponses: 6
    Dernier message: 30/06/2004, 22h36
  3. Réponses: 2
    Dernier message: 30/03/2004, 11h31
  4. Convertir une AnsiString en hexadecimal
    Par manathan01 dans le forum C++Builder
    Réponses: 3
    Dernier message: 26/12/2002, 09h27
  5. longueur d'une structure
    Par bohemianvirtual dans le forum C
    Réponses: 6
    Dernier message: 28/05/2002, 18h31

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