Для такого типа фильтрации значений я бы использовал предикат подтипа .
В вашем случае, измените ваше перечисление в соответствии с тем, что сказал Кит:
type Integers_Type is (ONE,TWO,THREE,FOUR,FIVE,SIX,SEVEN,EIGHT,NINE,TEN);
subtype Odd_Numbers_Type is Integers_Type
with Static_Predicate => Odd_Numbers_Type in ONE | THREE | FIVE | SEVEN | NINE;
Если вы хотите использовать числовые типы c вместо перечисления, используйте следующее
type Integers_Type is range 1 .. 10;
subtype Odd_Numbers_Type is Integers_Type
with Dynamic_Predicate => Odd_Numbers_Type mod 2 /= 0;
Для получения дополнительной информации вы можете прочитать обоснование
РЕДАКТИРОВАТЬ:
Для типов перечисления следующие компилируются с использованием gnatmake -gnata -gnatVa test_enum.adb , но предупреждает о строке 14 воздействия и не выполняется при выполнении из-за утверждения, выровненного для предиката stati c .
with Ada.Text_IO; use Ada.Text_IO;
Procedure Test_Enum is
type Integers_Type is (ONE,TWO,THREE,FOUR,FIVE,SIX,SEVEN,EIGHT,NINE,TEN);
subtype Odd_Numbers_Type is Integers_Type
with Static_Predicate => Odd_Numbers_Type in ONE | THREE | FIVE | SEVEN | NINE;
Test_I : Integers_Type := TWO;
Test_O : Odd_Numbers_Type := ONE;
begin
Put_Line("Test_I=" & Integers_Type'Image (Test_I));
Put_Line ("Test_O=" & Odd_Numbers_Type'Image (Test_O));
Test_O := Test_I;
Put_Line ("Test_O=" & Odd_Numbers_Type'Image (Test_O));
end Test_Enum;
Для целочисленных типов, используя команду компиляции gnatmake -gnata -gnatVa test_int.adb , компилятор предупреждает, что проверка завершится неудачно во время выполнения, что является подтверждением
with Ada.Text_IO; use Ada.Text_IO;
Procedure Test_Int is
type Integers_Type is range 1 .. 10;
subtype Odd_Numbers_Type is Integers_Type
with Dynamic_Predicate => Odd_Numbers_Type mod 2 /= 0;
Test_I : Integers_Type := 2;
Test_O : Odd_Numbers_Type := 1;
begin
Put_Line("Test_I=" & Integers_Type'Image (Test_I));
Put_Line ("Test_O=" & Odd_Numbers_Type'Image (Test_O));
Test_O := Test_I;
Put_Line ("Test_O=" & Odd_Numbers_Type'Image (Test_O));
end Test_Int;
В обоих случаях удаление флага -gnata сделает программу работающей без учета предиката, поскольку утверждения деактивированы.