7
votes

Disposition de la mémoire d'un ensemble

Comment est un défini code> organisé en mémoire dans Delphi?

Ce que j'essaie de faire est de casser un type simple à un type de jeu tel que p>

var
  ShiftState : TShiftState;
  MyNumber : Word absolute ShiftState;
begin
  MyNumber:=42;
end;


0 commentaires

4 Réponses :


1
votes

Vous devez choisir un type ordinal correctement dimensionné. Pour moi (D2007), votre code compile avec myNumber: octet : xxx

J'ai utilisé cette technique dans certaines situations et n'a pas rencontré de problèmes.


update

Le type Tshiftstate est prolongé depuis que Delphi 2010 devrait inclure deux nouveaux états, ssTouch et sspen , basé sur le Page DOC correspondante ( Page DOC actuelle ). Delphi 2009 DOC a toujours Tshiftstate défini comme un ensemble de 7 états.

Donc, votre tentative de convertir le mot sur Tshiftstate < / Code> fonctionnerait à Delphi 2010+, mais octet est la bonne taille de Delphi 2009.


3 commentaires

Merci pour ce nudge dans la bonne direction! J'ai cherché plus loin et j'ai trouvé ma réponse dans un autre fil. Au fait: dans Delphi Xe, le Tshiftstate contient 9 membres, alors je pense que nous devrions faire myNumber A mot , pas un < Code> octet plus.


@Heinrich: J'ai gardé cette page ouverte sans le rafraîchir depuis trop longtemps et n'a pas vu votre commentaire. Il est donc apparu que vous avez trouvé l'explication avant de le faire. Néanmoins, je pense que ma mise à jour ne fera pas de mal à la réponse de Ulrich. :)


@Andriy le plus d'informations le mieux. Que personne ne soit jamais confondu à nouveau par la mise en page des ensembles :)



1
votes

Malheureusement, je viens de savoir maintenant sur la question suivante: Delphi 2009 - Bug? Ajout de valeurs supposées invalides à un ensemble

La réponse acceptée de COSMIN contient une description très détaillée de ce qui se passe avec des ensembles à Delphi. Et pourquoi je ferais mieux d'utiliser mon approche avec absolu . Apparemment, une variable définie peut prendre de 1 à 32 octets de mémoire, en fonction des valeurs ENUM.


1 commentaires

Vous devriez utiliser quelque chose comme {$ si tailleof (set_in_question) <> Tailleof (tycast_var)} {$ Message Error}



6
votes

Un jeu DELPHI est un champ de bits Qui est des bits correspondant aux valeurs associées des éléments de votre ensemble. Pour un ensemble de types énumérés normaux, la disposition de bit est simple:

  • bit 0 correspond à l'élément défini avec la valeur ordinale 0
  • Bit 1 correspond à l'élément défini avec la valeur ordinale 1
  • et ainsi de suite.

    Les choses sont un peu intéressantes lorsque vous traitez avec un ensemble non contigu ou avec un ensemble qui ne démarre pas à 0. Vous pouvez le faire à l'aide du type de sous-arrangement de Delphi (exemple: de 3..7 ) ou en utilisant des types énumérés spécifiés la valeur ordinale réelle pour les éléments: xxx

    Dans de tels cas, Delphi allouera la quantité minimale requise de Les octets qui incluront tous les bits requis, mais ne «changeront» les valeurs de bit pour utiliser moins d'espace. Dans le Enumset Exemple Delphi utilisera deux octets:


1 commentaires

Cosmin, merci beaucoup pour la résumer! J'ai également beaucoup apprécié la lecture de vos tests dans le poste lié et recommander à tout le monde de le lire! Maintenant, tout est clair et moi et le compilateur est heureux :)



0
votes

J'utilise ceci:

pour <= 8 éléments, pbyte (@myNumber) ^, pour <= 16 éléments, pWord (@mynumber) ^, etc.

Si l'énumve prend plus de place (à travers l'option Min Enum Taille Compiler), cela fonctionnera toujours.


1 commentaires

J'irais pour octet (myenumvar) etc. et avoir les chèques de compilateur ajoutés. On peut écrire une paire de fonctions ordtomyenum et retour pour centraliser les moulages. Vous n'avez donc qu'un seul endroit pour changer si le type ENum devrait augmenter à la taille "suivante".