带字符串的Ada case语句

时间:2015-04-08 04:26:06

标签: string ada case-statement

我正在尝试在case语句中使用字符串,但是它给了我expected a discrete type. Found type Standard.String我理解字符串不是离散的。我想知道是否有工作。这是我的代码:

function Is_Valid_Direction(Direction_To_Go : in String) return Integer is
  Room : Integer := 0;
   begin
      --if (Direction_To_Go = "NORTH" or Direction_To_Go = "N") then
      --   Room := Building(currentRoom).exits(NORTH);
      --elsif (Direction_To_Go = "SOUTH" or Direction_To_Go = "S") then
      --   Room := Building(currentRoom).exits(SOUTH);
      --elsif (Direction_To_Go = "EAST" or Direction_To_Go = "E") then
      --   Room := Building(currentRoom).exits(EAST);
      --elsif (Direction_To_Go = "WEST" or Direction_To_Go = "W") then
      --   Room := Building(currentRoom).exits(WEST);
      --elsif (Direction_To_Go = "UP" or Direction_To_Go = "U") then
      --   Room := Building(currentRoom).exits(UP);
      --elsif (Direction_To_Go = "DOWN" or Direction_To_Go = "D") then
      --   Room := Building(currentRoom).exits(DOWN);
      --end if;
      case Direction_To_Go is
         when "NORTH" | "N" => Room := Building(currentRoom).exits(NORTH);
         when "SOUTH" | "S" => Room := Building(currentRoom).exits(SOUTH);
         when "EAST" | "E" => Room := Building(currentRoom).exits(EAST);
         when "WEST" | "W" => Room := Building(currentRoom).exits(WEST);
         when "UP" | "U" => Room := Building(currentRoom).exits(UP);
         when "DOWN" | "D" => Room := Building(currentRoom).exits(DOWN);
         when others => Room := 0;
      end case;
      return Room;
   end Is_Valid_Direction;

评论部分正是我想要的,但使用if语句。我只是想看一下案例陈述是否可能。

3 个答案:

答案 0 :(得分:6)

您可以将字符串映射到离散类型。最简单的是枚举类型:

procedure Light (Colour : in     String) is
   type Colours is (Red, Green, Blue);
begin
   case Colours'Value (Colour) is -- ' <- magic ;-)
      when Red =>
         Switch_Red_LED;
      when Green =>
         Switch_Green_LED;
      when Blue =>
         Switch_Blue_LED;
   end case;
exception
   when Constraint_Error =>
      raise Constraint_Error with "There is no " & Colour & " LED.";
end Light;

答案 1 :(得分:3)

我经常使用实际的map来执行此类映射,因为它比枚举更灵活。你的名字&#34;不必遵循枚举语法,您可以轻松提供所有映射到单个值的变体。

对于所需的功能定义,如包中所提供:

package Case_Map is

   function Is_Valid_Direction(Direction_To_Go : in String) return Integer;

end Case_Map;

这(由于缺少特定于游戏的声明而导致的非编译)实现使用字符串到枚举的映射,而枚举又是case表达式:

with Ada.Characters.Handling;
with Ada.Containers.Indefinite_Ordered_Maps;

package body Case_Map is

   use Ada.Characters.Handling;

   type Directions is (Go_North, Go_South, Go_East, Go_West, Go_Up, Go_Down);

   package Direction_Management is new Ada.Containers.Indefinite_Ordered_Maps
     (String, Directions);

   Direction_Map : Direction_Management.Map;

   function Is_Valid_Direction(Direction_To_Go : in String) return Integer is
      Room : Integer := 0;
   begin
      case Direction_Map(To_Upper(Direction_To_Go)) is
         when Go_North => Room := Building(CurrentRoom).Exits(NORTH);
         when Go_South => Room := Building(CurrentRoom).Exits(SOUTH);
         when Go_East => Room := Building(CurrentRoom).Exits(EAST);
         when Go_West => Room := Building(CurrentRoom).Exits(WEST);
         when Go_Up => Room := Building(CurrentRoom).Exits(UP);
         when Go_Down => Room := Building(CurrentRoom).Exits(DOWN);
      end case;
      return Room;
   exception
      when Constraint_Error =>
         return 0;
   end Is_Valid_Direction;

begin
   Direction_Map.Insert("NORTH", Go_North);
   Direction_Map.Insert("N", Go_North);
   Direction_Map.Insert("SOUTH", Go_South);
   Direction_Map.Insert("S", Go_South);
   Direction_Map.Insert("EAST", Go_East);
   Direction_Map.Insert("E", Go_East);
   Direction_Map.Insert("WEST", Go_West);
   Direction_Map.Insert("W", Go_West);
   Direction_Map.Insert("UP", Go_Up);
   Direction_Map.Insert("U", Go_Up);
   Direction_Map.Insert("DOWN", Go_Down);
   Direction_Map.Insert("D", Go_Down);
end Case_Map;

答案 2 :(得分:0)

GNAT编译器本身使用将字符串(标识符,关键字......)映射到整数的哈希表。这是包namet.adsGNATCOLL.Symbolic提供了类似的API。这简化了许多事情(比如字符串比较要快得多),并允许在示例中使用case语句。因此,如果您使用有限(或至少增长缓慢)的字符串列表,GNATCOLL.Symbolic可能是一种合适的方法