в случае массива, коль скоро
ХЗ: SST_Data; -- Правильно, конкретный тип
А2: Airplane_Data'Class := Х2; -- Правильно, ограничен
A3: Airplane_Data'Class := ХЗ; --Правильно, ограничен
Как и в случае массива, коль скоро CW-объект ограничен, его ограничения изменить нельзя. CW-тип можно использовать в декларации локальных переменных подпрограммы, которая получает параметр CW-типа. Здесь снова полная аналогия с массивами:
procedure P(S: String; С: in Airplane_Data'Class) is
Local_String: String := S;
Local_Airplane: Airplane_Data'Class := C;
Begin
…
end P;
Динамический полиморфизм имеет место, когда фактический параметр имеет тип класса, в то время как формальный параметр — конкретного типа, принадлежащего классу:
with Airplane_Package; use Airplane_Package;
with SST_Package; use SST_Package;
procedure Main is
procedure Proc(C: in out Airplane_Data'Class; I: in Integer) is
begin
Set_Speed(C, I); -- Какого типа С ??
end Proc;
A: Airplane_Data;
S: SST_Data;
begin -- Main
Proc(A, 500); -- Вызвать с Airplane_Data
Proc(S, 1000); -- Вызвать с SST_Data end Main:
Фактический параметр С в вызове Set_Speed имеет тип класса, но имеются две версии Set_Speed с формальным параметром либо родительского типа, либо производного типа. Во время выполнения тип С будет изменяться от вызова к вызову, поэтому динамическая диспетчеризация необходима, чтобы снять неоднозначность вызова.
Рисунок 14.6 поможет вам понять роль формальных и фактических параметров в диспетчеризации. Вызов Set_Speed вверху рисунка делается с фактическим параметром типа класса. Это означает, что только при вызове подпрограммы мы знаем, имеет ли фактический параметр тип Airplane_Data или SST_Data.