Question

Je suis juste essayer d'obtenir le blocage d'unités utilisées pour rendre le code plus encapsulées. Je suis en train de faire les déclarations publiques / privées de mes méthodes triées, donc je peux les appeler d'autres unités qui utilisent testunit. Dans cet exemple, je veux rendre publics de hellofromotherunit, mais stickletters privé.

unit testunit;    

interface

uses
  Windows, Messages, Dialogs;    

implementation

function stickletters(a,b:string):string;
begin
  result:=a+b;
end;

procedure hellofromotherunit();
begin
 showmessage(stickletters('h','i'));
end;

end.

Je ne semblait pas pouvoir copier la structure publique / privée d'autres unités comme dans:

Type
private
function stickletters(a,b:inter):integer;
public
procedure hellofromotherunit();
end
Était-ce utile?

La solution

La structure de l'appareil ressemble un peu les sections publiques / privées des objets, on pourrait dire qu'il est leur ancêtre. Mais la syntaxe est différente.

Il vous suffit de déclarer l'en-tête de la méthode dans la section d'interface, comme dans:

interface
  procedure hellofromotherunit();

implementation
  procedure hellofromotherunit(); begin .. end;

Une seule de chaque section autorisée.

Autres conseils

privé et public uniquement appliquée aux classes.

Qu'est-ce que vous voulez faire est de mettre une copie de la déclaration de hellofromotherunit dans la section d'interface. Ne pas mettre une copie de la déclaration de stickletter là, cependant.

Tout ce qui apparaît dans la section d'interface est effectivement public. Tout ce qui est seulement dans la mise en œuvre est privé.

En outre,

Chaque unité comporte deux parties distinctes. L'interface et la mise en œuvre.

La section d'interface contient toutes les définitions publiques (types, les titres de la procédure, les constantes). La section de mise en œuvre contient tous les détails de mise en œuvre.

Lorsque vous utilisez une unité, (en utilisant la clause uses), vous aurez accès aux définitions publiques de cette unité. Cet accès n'est pas récursive, donc si l'unité Une interface utilise l'unité B, et l'unité C utilise l'unité A, vous ne recevez pas l'accès à l'unité B sauf si vous utilisez explicitement.

La section de mise en œuvre a accès à l'interface, à l'unité utilisé dans les deux utilisations clauses (interface et la mise en œuvre).

Les interfaces d'unités utilisées sont d'abord compilées avant qu'il continue de compiler le reste. Ceci a l'avantage que vous pouvez avoir des dépendances circulaires à partir de la mise en œuvre:

unit A;
interface
uses B;

unit B;
interface
implementation
uses A;

compilant:

  • essayer l'interface A, B fail besoin
  • essayez l'interface B, ok!
  • essayer l'interface A, ok!
  • essayer la mise en œuvre A, ok!
  • essayer l'application B, ok!

Chaque unité possède également une section d'initialisation (et si elle a une section d'initialisation, il pourrait également avoir une section de finalisation.) La section d'initialisation est utilisé pour initialiser les variables de l'appareil. Les sections de finalisation sont utilisés pour le nettoyage. Lorsque vous utilisez, il est sage de ne pas compter sur initialisations d'autres unités. Il suffit de les garder simple et court.

Unité sont également des espaces de noms. Considder ce qui suit:

unit A;
interface
const foo = 1;

unit B;
interface
const foo = 2;

unit C;
interface
uses A, B;

const
  f1 = foo;
  f2 = A.foo;
  f3 = B.foo;

Si un identifiant est défini dans plusieurs unités utilisées, la dernière unité possible dans la liste des utilisations est prise. Alors f1 = 2. Mais vous pouvez le préfixe avec le nom unité (espace de noms) pour résoudre ce problème.

Avec l'introduction de .net, plusieurs espaces de noms partiels sont autorisés qui introduit d'autres problèmes agréable:

unit foo;
interface
type
  rec1 = record
    baz : Boolean;
  end;
var
  bar : rec1;

unit foo.bar;
interface
var
  baz : Integer;

uses
  foo, foo.bar;    
begin
  foo.bar.baz := true;
  foo.bar.baz := 1;
end.  

// 1. Which these lines gives an error and why?
// 2. Does the result change if you write uses foo.bar, foo?

Dans ce cas, vous avez un conflit. Mais cela est résolu en donnant des noms d'espaces de noms plus haute priorité. Ainsi, la première ligne échoue.

Il suffit de ne pas déclarer la méthode dans la section interface et il sera maintenu privé.

unit Unit2;

interface
  function MyPublicFunction():Boolean;

implementation

function MyPrivateFunction():Boolean;
begin
  // blah blah
end;

function MyPublicFunction():Boolean;
begin
  // blah blah
end;
end.
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top