我需要有关在Ada中隐藏运算符的指导,同时仍然从声明类型的包体中调用它。
我在一个包中有一个类型,其中通过将运算符定义标记为抽象来隐藏一些内部运算符,因为从语义上讲它是无意义的。但是我仍然需要正文中的运算符,以便可以比其变通方法更有效地计算其他运算。有没有办法将运算符标记为在体内不抽象,即使它在规范中是抽象的?或者我是否需要声明一个新的等效函数,并从Intrinsics导入?
有问题的运算符为*
和/
。
答案 0 :(得分:4)
我不相信你可以将操作员标记为在体内不抽象"。
重新导入内在的一种相当简洁的方式是
package Abstracting is
type T is new Integer;
function "+" (L, R : T) return T is abstract;
function Add (L, R : T) return T;
end Abstracting;
(我猜测你的实际类型 - 它必须是明显的数字,或者"+"
,"/"
首先不会成为问题。
然后,
package body Abstracting is
package Intrinsics is
function "+" (L, R : T) return T with Import, Convention => Intrinsic;
end Intrinsics;
好的,重新导入"+"
。现在让它可见:
use Intrinsics;
function Add (L, R : T) return T is
begin
return L + R;
使用包"+"
中Intrinsics
的版本(我尝试将use
放在Add
内但不起作用。必须非常接近边缘这里:))
end Add;
end Abstracting;
答案 1 :(得分:1)
通常,将公共定义设为私有,并且仅声明对抽象有意义的操作。这留下了正文中可用的完整类型的未定义但固有的操作:
package P is
type T is private;
function "+" (Left : T; Right : T) return T;
function "-" (Left : T; Right : T) return T;
private -- P
type T is range ...;
end P;
这种方法的难点不在于使用未定义的操作,而是在您需要使用已被覆盖的内在操作时:" +"和" - "在这种情况下。这通常通过导出T,将值转换为父类型以执行操作,然后转换回T来解决:
private -- P
type Raw is range ...;
type T is new Raw;
end P;
然后你可以使用" +"和" - "对于pkg身体中的Raw:
function "+" (Left : T; Right : T) return T is
(T (Raw (Left) + Raw (Right) ) );