Спецификация пакета
Как уже говорилось, спецификация пакета Ады определяет интерфейс доступа к вычислительным ресурсам (сервисам) пакета.
Она может содержать описания типов, переменных, констант, спецификации подпрограмм, других пакетов, - все то, что должно быть доступно тому, кто будет использовать данный пакет.
Простой пример спецификации пакета может иметь следующий вид:
package Odd_Demo is
type A_String is array (Positive range <>) of Character; Pi : constant Float := 3.14; X : Integer; type A_Record is record Left : Boolean; Right : Boolean; end record; -- примечательно, что дальше, для двух подпрограмм представлены только -- их спецификации, тела этих подпрограмм будут находиться в теле пакета procedure Insert(Item : in Integer; Success : out Boolean); function Is_Present(Item : in Integer) return Boolean; end Odd_Demo; |
Мы можем получить доступ к этим сервисам в нашем коде путем указания данного пакета в спецификаторе совместности контекста with, а затем использовать полную точечную нотацию.
Полная точечная нотация, в общем случае, имеет следующий вид:
имя_пакета.имя_используемого_ресурса |
где имя_используемого_ресурса - это имя типа, подпрограммы, переменной и т.д.
Для демонстрации сказанного приведем схематический пример процедуры которая использует показанную выше спецификацию:
with Odd_Demo;
procedure Odder_Demo is My_Name : Odd_Demo.A_String; Radius : Float; Success : Boolean; begin Radius := 3.0 * Odd_Demo.Pi; Odd_Demo.Insert(4, Success); if Odd_Demo.Is_Present(34) then ... . . . end Odder_Demo; |
Не трудно заметить, что доступ к ресурсам пакета, текстуально подобен доступу к полям записи.
В случаях, когда использование полной точечной нотации для доступа к ресурсам пакета обременительно, можно использовать инструкцию спецификатора использования контекста use.
Это позволяет обращаться к ресурсам которые предоставляет данный пакет без использования полной точечной нотации, так, как будто они описаны непосредственно в этом же коде.
with Odd_Demo; use Odd_Demo; procedure Odder_Demo is My_Name : A_String; Radius : Float; Success : Boolean; begin Radius := 3.0 * Pi; Insert(4, Success); if Is_Present(34) then ... . . . end Odder_Demo; |
В этом случае можно избавиться от двусмысленности путем возвращения к использованию полной точечной нотации для соответствующих ресурсов.
------------------------------- package No1 is A, B, C : Integer; end No1; ------------------------------- package No2 is C, D, E : Integer; end No2; ------------------------------- with No1; use No1; with No2; use No2; procedure Clash_Demo is begin A := 1; B := 2; C := 3; -- двусмысленность, мы ссылаемся -- на No1.c или на No2.c? No1.C := 3; -- избавление от двусмысленности путем возврата No2.C := 3; -- к полной точечной нотации end Clash_Demo; |
В этом случае также можно избавиться от двусмысленности путем использования полной точечной нотации.
package No1 is A : Integer; end No1; with No1; use No1; procedure P is A : Integer; begin A := 4; -- это - двусмысленно P.A := 4; -- удаление двусмысленности путем указания -- имени процедуры в точечной нотации No1.A := 5; -- точечная нотация для пакета end P; |