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

Langage C++ Discussion :

Adresse case mémoire - taille max


Sujet :

Langage C++

  1. #1
    Candidat au Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    2
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2011
    Messages : 2
    Points : 3
    Points
    3
    Par défaut Adresse case mémoire - taille max
    Bonjour,

    Je souhaiterai, pour des raisons de respect d'une norme, stocker d'adresse des cases mémoires servants de têtes de listes chainées (de types différents)
    Je pensais stocker cela sous forme de tableau de int. Or ce dernier ne peut contenir que des valeurs inférieures à 2 147 483 648. (4 294 967 295 si unsigned)
    Ex : int data[N];
    data[0] = &entreprises;
    data[1] = &comptes;
    ...
    Essayant d'envisager toutes les possibilités de bug, ma question est la suivante :

    Avec la mémoire toujours plus grande des postes informatiques,
    Est-ce que l'adresse d'une case mémoire pourrait dépasser le simple int ?
    Si oui, auriez-vous des idées pour pallier à ce problème ?

    Cdlt,
    Skealios

  2. #2
    Membre régulier
    Homme Profil pro
    Ingénieur
    Inscrit en
    Octobre 2006
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Ingénieur
    Secteur : Transports

    Informations forums :
    Inscription : Octobre 2006
    Messages : 48
    Points : 97
    Points
    97
    Par défaut
    Bonjour,

    Suivant l'utilisation, les types suivants me paraissent plus appropriés que int :

    - void* : type de pointeur "générique" (pouvant pointer sur n'importe quoi/n'importe quel type de données)
    - size_t : type pouvant contenir la taille maximale d'un objet sur une architecture donnée

  3. #3
    Expert éminent sénior
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 614
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 52
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 614
    Points : 30 626
    Points
    30 626
    Par défaut
    Citation Envoyé par skealios Voir le message
    Bonjour,

    Je souhaiterai, pour des raisons de respect d'une norme, stocker d'adresse des cases mémoires servants de têtes de listes chainées (de types différents)
    Je pensais stocker cela sous forme de tableau de int. Or ce dernier ne peut contenir que des valeurs inférieures à 2 147 483 648. (4 294 967 295 si unsigned)
    Ex : int data[N];
    data[0] = &entreprises;
    data[1] = &comptes;
    ...
    Essayant d'envisager toutes les possibilités de bug, ma question est la suivante :

    Avec la mémoire toujours plus grande des postes informatiques,
    Est-ce que l'adresse d'une case mémoire pourrait dépasser le simple int ?
    Très largement.

    Rien qu'au niveau de la ram, les machines actuelles disposent de... 16 Gb de ram.

    Bien sur, les systèmes d'exploitation imposent régulièrement des limites quant à la quantité de mémoire qu'une application peut utiliser, mais les OS 64 bits la placent généralement bien au delà des valeurs d'un int.
    Si oui, auriez-vous des idées pour pallier à ce problème ?
    Classiquement, une adresse mémoire est représentée sous la forme d'un pointeur.

    Ou, pour être plus juste, un pointeur ne sera jamais qu'une valeur numérique non signée dont la taille (en terme de nombre de bits utilisés pour représenté cette valeur) est au minimum suffisante pour pouvoir représenter l'ensemble des valeurs (comprends: des adresses mémoires) accessibles sur le système utilisé.

    Evidemment, cela sous entend
    1. que la taille d'un pointeur sera différente en fonction de l'OS pour lequel l'application a été compilée (généralement 32 bits sur les OS 32 bits, 64 bits sur les OS 64 bits, mais Mac Osx utilise une taille de 40 bits pour ses pointeurs )
    2. que la représentation de l'adresse en elle-même en mémoire est soumise au boutisme de la machine.
    3. que les pointeurs sont généralement associés à l'allocation dynamique de la mémoire et que tu ne peux donc utiliser cette adresse que dans le cadre d'une exécution
    4. que si tu essayes de (dé) sérialiser cette information, tu risque d'avoir de sérieux problèmes
    size_t permet de représenter la taille (en nombre de byte) de n'importe quel objet en mémoire, mais cela ne signifie aucunement qu'il permet de représenter n'importe quelle adresse (il peut en effet y avoir une restriction quant à la taille qu'un objet peut prendre en mémoire différente de la restriction en terme de limites d'adresses accessibles), mais un pointeur étant par nature un pointeur, tu peux considérer que n'importe quel pointeur peut représenter l'adresse à laquelle se trouve n'importe quel type d'objet.

    La seule différence notable entre un pointeur sur un objet de type T et un pointeur sur un objet de type S se trouvant au niveau de l'arithmétique des pointeurs: si le pointeur sait travailler sur un type T, l'adresse résultant d'un (adresse +1) correspondra au décalage d'un nombre de byte correspondant à la taille prise en mémoire par le type T, et il en ira de même pour le type S.

    Si problème il doit y avoir, ce sera à cause de cette arithmétique des pointeurs car si tu considère que ton type pointe sur un objet de type T alors qu'il pointe en réalité sur un objet de type S, le résultat de (adresse +1) risque de t'emmener vers une adresse qui ne correspond pas au premier byte effectif de ton type.

    Evidemment, le problème s'accentuera encore sur les types complexes (manipulant différentes données, dont les tailles en mémoire sont différentes... ou non) car l'accès à un membre donné du type se fera de la même manière.

    Tu peux donc parfaitement envisager de placer la tête de tes différentes liste dans un tableau de pointeur sur void* en utilisant, de préférence, le reinterpret_cast (uniquement pour pouvoir retrouver facilement les endroits où le transtypage est effectué dans ton code ) plutôt que le transtypage "C style"), sous une forme proche de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    int main(){
        /* je fais simple pour l'exemple, il faudra sans doute quelque chose de plus
         * correct :D
         */
        void * tab[10];
        Liste1 l1;
        Liste2 l2;
        /* on considère que l'on peut accéder à la tête de liste sous la forme
         * d'un pointeur vers l'élément avec first quel que soit le type de la liste;))
         */
        tab[0] = reinterpret_cast<void*>(l1.first);
        tab[1] = reinterpret_cast<void*>(l2.first);
    }
    Mais il s'agira d'être particulièrement prudent au moment d'accéder à ces données car l'objet pointé sera du type Liste1::element_type pour tab[0] et de type Liste2::element_type pour tab[1].

    Il faudra donc s'assurer que tu fera bel et bien correctement le transtypage inverse avant d'essayer d'accéder à quoi que ce soit

    [EDIT]Ceci dit, une norme obligeant à travailler de la sorte oblige, de facto, de faire un travail dégueulasse, jetant à l'eau toute approche OO un minimum correcte.

    As tu la moindre influence sur cette norme
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  4. #4
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Plutôt intptr_t que size_t, en fait.
    Citation Envoyé par skealios Voir le message
    Avec la mémoire toujours plus grande des postes informatiques,
    Est-ce que l'adresse d'une case mémoire pourrait dépasser le simple int ?
    OUI. Les deux modèles 64-bits les plus utilisés (LP64 et LLP64) sont dans ce cas: Les int sont toujours 32 bits, les pointeurs 64 bits.
    Si oui, auriez-vous des idées pour pallier à ce problème ?
    Utiliser les types ayant la même taille que les pointeurs (intptr_t, uintptr_t, size_t...)
    Ou, quand c'est approprié, utiliser directement des pointeurs, y compris void*.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  5. #5
    Candidat au Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    2
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2011
    Messages : 2
    Points : 3
    Points
    3
    Par défaut
    Bonjour,

    Merci de vos réponses.
    Effectivement, Void* me semble être une bonne solution.

    As tu la moindre influence sur cette norme
    Non, celle-ci m'est imposée.
    Plus simplement, elle m'impose de réunir mes listes dans un seul point de départ.

    Néanmoins, en lisant vos réponses, elles m'ont amenés à penser à une solution que je n’avais pas envisagée.
    Connaissant déjà tous les éléments dont j'ai besoin et leur type, je vais plutôt utiliser une simple structure contenant le point de départ de chacune de mes chaines, cela me semble plus simple à mettre en place et ne nécessitera pas de contrôle spécifique.

    Merci pour l'aide et les informations.

    Cdlt,
    Skealios

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

Discussions similaires

  1. La taille max de la mémoire de la JVM
    Par abou_alkassim dans le forum API standards et tierces
    Réponses: 6
    Dernier message: 14/12/2006, 11h43
  2. Réponses: 5
    Dernier message: 28/10/2004, 15h22
  3. [JTextFiled]Mettre une taille max à la saisie
    Par mush_H dans le forum Composants
    Réponses: 13
    Dernier message: 29/07/2004, 11h22
  4. Taille Max que peux gerer un serveur SQL
    Par Youssef dans le forum MS SQL Server
    Réponses: 2
    Dernier message: 27/07/2004, 11h52
  5. taille max du nom d'un champ
    Par hna dans le forum Paradox
    Réponses: 2
    Dernier message: 28/07/2002, 02h40

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