首页 > 解决方案 > 如何将枚举转换为整数以处理溢出/环绕?

问题描述

我正在学习 ada,我正在尝试为枚举实现附加重载。

基本上我希望能够将 Integer 添加到 Day 类型并获得生成的 Day 值。所以星期一 + 2 => 星期三。

这是我的简化代码:

procedure overload is                                                                                                             
    type Day is (                                                                                                                 
        Sunday,                                                                                                                   
        Monday,                                                                                                                   
        Tuesday,                                                                                                                  
        Wednesday,                                                                                                                
        Thursday,                                                                                                                 
        Friday,                                                                                                                   
        Saturday                                                                                                                  
    );
    day1 : Day := Monday;
    function "+" (left: Day; right: Integer) return Day is                                                                        
        -- how would I handle this here? I want to basically say
        -- if Day + Integer > Saturday then
        --   wraparound back to Sunday
        return DayValue;
    begin
       for x in 0 .. 7 loop
          Ada.text_io.put_line("Monday + " & Integer'Image(x) & " = " & Day'Image(day1 + x));
       end loop;
end overload;

标签: ada

解决方案


您可以使用 'Pos 和 'Val 属性来执行此操作。'Pos 返回所提供日期相对于第一个选项(索引为 0)的位置,而 'Val 采用 Pos 值并返回日期类型值:

return Day'Val(Day'Pos(Left) + Right);

对于环绕检查'星期六的 Pos 值与'左的 Pos 值 + 右值并使用 Day'Val(0) 表示星期日

或者将您的输入类型 Right 从 Integer 切换为 Natural 并使用模数数学:

return Day'Val((Day'Pos(left) + Right) mod 7);

您甚至可以花哨并为 7 设置一个常数:

Day_Mod : constant := Day'Pos(Day'Last) - Day'Pos(Day'First) + 1;

然后它变成

return Day'Val((Day'Pos(left) + Right) mod Day_Mod);

推荐阅读