6

我继承了这段代码,无法弄清楚它的作用。定义看起来很简单:

result : BOOLEAN ;
LOOKUP_TABLE : array
  ( BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN,
    BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN, BOOLEAN ) of
  BOOLEAN := (others => (others => (others => (others => (others => (others => (others => (others =>
             (others => (others => (others => (others => (others => (others => (others => (others => 
                TRUE ))))))))))))))));

在正文中,它的用法如下:

result := LOOKUP_TABLE(TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE,
                       FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE );

在 GDB 中转储 lookup_table 时,它​​会创建一个超过 500,000 个字符长的行,第一个部分看起来像这样:

$1 = ((((((((((((((((true, true), (true, true)), ((true, true), (true, true))), (((true, true), (true, ...

最初我的问题是:如何将 16 个布尔数组简化为单个布尔“结果”?但在 GDB 中查看后,我不得不问“这是什么东西???”

PS:在body中调用之后,LOOKUP_TABLE还是500,000个字符,其中每个布尔字段都是TRUE...

4

5 回答 5

7

这不是一个 16 布尔数组。它是一个 16数组,每个维度的范围从falsetrue,因此它有 2个 16或 65536 个元素。

于 2013-07-22T18:22:28.877 回答
7

在 Ada 中,数组不一定由从 0 开始的 int 索引。在这种情况下,您有一个以布尔值作为索引的多维数组。

初始化数组时,必须指定数组的整个范围。

一维数组如下所示:

Lookup_Table : array(Boolean) of Boolean := (False..True => True);

在处理较大的数组时,指定所有备选方案很不方便,因此使用关键字others. 这意味着尚未指定所有替代方案,因此与上述相同:

Lookup_Table : array(Boolean) of Boolean := (others => True);

这个数组现在看起来像这样(1 是维度,C 是内容):

   1  |  C
 -----|-----
 False|True
 True |True

在二维数组中,这将是:

Lookup_Table : array(Boolean, Boolean) of Boolean := (others => (others => True));

   1  |  2  |  C
 -----|-----|-----
 False|False|True
 False|True |True
 True |False|True
 True |True |True

在您的情况下,它是 16 维。

您可以在此处阅读有关 Ada 数组的更多信息

于 2013-07-22T18:34:43.973 回答
2

如果我这样做,并且表中感兴趣的值相对较少,我可能会使用带有多部分键的 Map:

with Ada.Containers.Indefinite_Ordered_Maps;

package Bool_16_Mapping is

   Key_Arity : constant := 16;

   type Key_Range is range 1 .. Key_Arity;

   type Bool_16_Keys is array (Key_Range) of Boolean;

   package Bool_16_Array_Management is
     new Ada.Containers.Indefinite_Ordered_Maps
       (Bool_16_Keys, Boolean);

end Bool_16_Mapping;

然后将感兴趣的值插入到地图中。在执行期间,使用短路Contains() 然后 Element(),或者编写一个小函数来完成。这是一个例子:

with Ada.Text_IO; use Ada.Text_IO;
with Bool_16_Mapping;

procedure Bool_16_Map_Test is

   Lookup_Table : Bool_16_Mapping.Bool_16_Array_Management.Map;

   Working_Key : Bool_16_Mapping.Bool_16_Keys := (others => False);

   function Get_Result (P1,   P2,  P3,  P4,
                        P5,   P6,  P7,  P8,
                        P9,  P10, P11, P12,
                        P13, P14, P15, P16 : Boolean) return Boolean is
      Key : Bool_16_Mapping.Bool_16_Keys := 
        (P1,  P2,  P3,  P4,  P5,  P6,  P7,  P8,
         P9, P10, P11, P12, P13, P14, P15, P16);
      Result : Boolean := False;
   begin
      if Lookup_Table.Contains(Key) then
         Result := Lookup_Table.Element(Key);
      end if;
      return Result;
   end Get_Result;

   Lookup_Result : Boolean;

   use type Bool_16_Mapping.Key_Range;

begin
   -- Initialize the table with some values
   for K in Bool_16_Mapping.Key_Range loop
      Working_Key (K) := True;
      Lookup_Table.Insert(Working_Key, K mod 2 = 0);
   end loop;

   Lookup_Result := Get_Result
     (True, True, True, False, False, False, False, False,
      False, False, False, False, False, False, False, False);
   Put_Line("#1: " & Boolean'Image(Lookup_Result));

   Lookup_Result := Get_Result
     (True, True, True, True, False, False, False, False,
      False, False, False, False, False, False, False, False);
   Put_Line("#2: " & Boolean'Image(Lookup_Result));

   Lookup_Result := Get_Result
     (False, True, True, False, False, False, False, False,
      False, False, False, False, False, False, False, False);
   Put_Line("#3: " & Boolean'Image(Lookup_Result));

end Bool_16_Map_Test;
于 2013-07-23T18:38:18.147 回答
1

这种东西通常代表指示某些权限的标志。IE。

IsAdmin CanEdit CanInsert CanDelete

因此,如果某人是管理员并且可以编辑但不能插入或删除,它将是:1100。也许这个大数组的含义相同。

于 2013-07-22T18:26:40.030 回答
0

选择这可能是因为值是稀疏的。我认为您可以替换为单个 64K 布尔数组,即 8K 字节数组(8192 个无符号字符)。最初设置为 0,然后将每个使用的条目设置为 1,对密钥进行位或运算。

于 2013-07-22T18:33:47.003 回答