Question

Ce code dans une application graphique est compilé et exécuté:

procedure TForm1.Button1Click(Sender: TObject);
begin
  Self := TForm1.Create(Owner);
end;

(testé avec Delphi 6 et 2009)

  • pourquoi l'auto est-il accessible en écriture et non en lecture seule?
  • dans quelles situations cela pourrait-il être utile?

Modifier:

  • Est-ce également possible dans Delphi Prism? (Je pense que oui, voir ici .

Mise à jour: Applications / bibliothèques Delphi utilisant l'attribution automatique:

Était-ce utile?

La solution

Ce n'est pas aussi grave que cela pourrait être. Je viens de le tester dans Delphi 2009, et il semblerait que, même si le paramètre Self n'utilise pas la sémantique const , ce que vous semblez vouloir dire, il n'utilise pas non plus . var sémantique, afin que vous puissiez la modifier à votre guise dans votre méthode sans perdre la référence que l'appelant détient à votre objet. Ce serait une très mauvaise chose.

Quant à la raison pour laquelle l’une des deux réponses. Soit un simple oubli, soit ce que Marco a suggéré: vous permettre de passer Self à un paramètre var .

Autres conseils

Peut-être pour permettre de passer aux paramètres const ou var?

Cela pourrait être un artefact, car le système ne dispose d'aucun self à gauche du signe: =.

Céder à soi-même est tellement illogique et inutile que cette "fonctionnalité" est probablement un oubli. Et comme pour les constantes assignables, il n’est pas toujours facile de corriger de tels problèmes.

Le conseil simple est le suivant: ne le faites pas.

En réalité, "Self" est simplement une référence de nom à un emplacement de la pile dont l'adresse de magasin pointant vers un objet du tas. Il est possible de forcer la lecture seule sur cette variable, apparemment le concepteur a décidé de ne pas le faire. Je pense que la décision est arbitraire.

Vous ne pouvez voir aucun cas où cela est utile, cela changerait simplement une valeur dans la pile. De plus, changer cette valeur peut être dangereux, car rien ne garantit que le code du membre de l'instance de référence sera cohérent d'une version à l'autre du compilateur.

Mise à jour: En réponse au commentaire PatrickvL

  

La 'variable' " Self " n'est pas sur le   stack (à ma connaissance, ce n'est jamais le cas);   Au lieu de cela sa valeur est mise dans un   inscrivez-vous (EAX pour être exact) juste avant   un appel à une méthode d'objet est effectué. -

Non, Self a une adresse réelle dans la mémoire. Essayez ce code pour voir par vous-même.

procedure TForm1.Button1Click(Sender: TObject);
begin
  ShowMessage(IntToStr(Integer(@Self)));
end;

procedure TForm1.Button2Click(Sender: TObject);
var
  newform: TForm;
  p: ^Integer;
begin
  Self.Caption := 'TheOriginal';
  newform := TForm.Create(nil);
  try
    newform.Caption := 'TheNewOne';
    // The following two lines is, technically, the same as
    //   Self := newform;
    p := Pointer(@Self);
    p^ := Integer(newform);
    ShowMessage(Self.Caption);  // This will show 'TheNewOne' instead of 'TheOriginal'
  finally
    Self.Free; // Relax, this will free TheNewOne rather than TheOriginal
  end;
end;

Parfois, lorsque vous souhaitez optimiser une méthode aussi loin que vous le pouvez (sans recourir à l'assemblage), 'Self' peut être utilisé (ab) comme une variable 'libre' - cela pourrait simplement faire la différence entre en utilisant une pile et en utilisant des registres.

Bien sûr, le contenu de la pile est probablement déjà présent dans le cache de la CPU, il devrait donc être rapide à accéder, mais les registres sont encore plus rapides.

Sidenote: Il me manque encore le temps où je programmais sur le Motorola 68000 de l'Amiga et qui disposait du luxe de 16 registres de données et de 16 registres d'adresses ... Je ne peux pas croire que le monde ait choisi le modèle Limité à 4 registres de la ligne de processeurs 80x86!

Et pour finir, je choisis parfois d'utiliser Self, l'optimiseur de Delphi étant, eh bien, pas l'optimisation , en fait. (Au moins, cela n’est guère comparable à ce que l’on peut trouver dans les divers optimiseurs LLVM, par exemple.) IMHO, et YMMV bien sûr.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top