Ada 2012中正式不完整类型的规则

时间:2015-11-03 10:27:45

标签: generics ada

根据AI05-213,现在可以使用不完整类型来实例化泛型。我想用它来构建不透明的容器:几个包定义私有类型和匹配容器。但是,我希望容器派生自一个常见的Containers.Container类型,它可以提供一些简单的子程序(例如Clear,Is_Empty,Iterate)。对于后者,需要存储在容器中的元素类型,因此包容器必须是通用的。

我无法编译代码,所以我进行了一些实验。似乎我可以使用标记类型,但不能使用类范围类型,也不能使用标记类型的子类。

为什么会这样?知道如何实现一个简单的容器抽象,它可以使用私有元素,并使用各种具体容器(例如Map,Linked List,Set)?

用于测试的代码:

actual.ads

with Containers;

package Actual is
   type Element is tagged private;
   type Sub_Element is new Element with private;
   package List is new Containers (Element_Type => Element'class); --error
   package Another is new Containers (Element_Type => Element); --ok
   package Still_Another is new Containers (Element_Type => Sub_Element); --error
private
   type Element is tagged null record;
   type Sub_Element is new Element with null record;
end Actual;

containers.ads

generic
   type Element_Type (<>) is tagged;
package Containers is
   type Container is abstract tagged null record;
end Containers;

1 个答案:

答案 0 :(得分:3)

[HttpPost] public ActionResult Edit(EditWorkflowViewModel viewModel) { //... Code to persist the viewModel Data... viewModel.Test = "changed"; if (Request.IsAjaxRequest()) return PartialView("_Edit", viewModel); return View("_Edit", viewModel); } 类型移动到另一个包会改变整个问题,因为不再存在过早使用带有私有组件的类型的问题。它可能是一个编译器错误(当前的Pro版本仍然显示两个错误),但我不太确定。

在实践中,我认为使用像你这样的不完整类型不太可能非常有用。对于容器包中的Element,基本上没什么可以做的,因为除了它被标记之外,你对它一无所知。你不能存储这样一个元素(这是不确定的)。

使用动态调度对性能来说也是非常糟糕的。我最近花了很多时间测量东西,我建议你尽早做好设计。您将看到动态调度的成本非常昂贵。我自己的经验是,最好使用泛型来实现这种方法。如果我可能被允许使用无耻的插件,如果您正在设计容器,您可能会发现最近的博客文章很有趣:http://blog.adacore.com/traits-based-containers