C++ C+中的自由定理+;:模板对于未知类型的对象是否天生无知和中立?

C++ C+中的自由定理+;:模板对于未知类型的对象是否天生无知和中立?,c++,templates,abstraction,type-systems,type-theory,C++,Templates,Abstraction,Type Systems,Type Theory,在Haskell中有一个著名的例子,如果我们有一个没有具体类型的函数,我们可以推断出它的行为 f : a -> a 永远是身份 对于Java泛型,我们无法证明泛型函数具有某种行为,因为我们可以使用instanceof或对象基类上的方法来绕过这些限制,但是如果我看到带有签名的方法 <T> List<T> reverse(List<T> list) 列表反转(列表) 可以合理地假设函数不会使用任何类型为t的属性 模板化C++函数的类型签名似乎没有提供任

在Haskell中有一个著名的例子,如果我们有一个没有具体类型的函数,我们可以推断出它的行为

f : a -> a
永远是身份

对于Java泛型,我们无法证明泛型函数具有某种行为,因为我们可以使用
instanceof
对象
基类上的方法来绕过这些限制,但是如果我看到带有签名的方法

<T> List<T> reverse(List<T> list)
列表反转(列表)
可以合理地假设函数不会使用任何类型为t的属性


模板化C++函数的类型签名似乎没有提供任何关于它实现的提示。是否有任何特性,现有的或建议的标准,这将允许我们编写函数签名提供类似的扣除在C++中?例如,用某种方式说“此函数适用于任何类型”。

也许您指的是C++20约束和概念:

类模板、函数模板和非模板函数 (通常是类模板的成员)可能与 约束,指定对模板参数的要求, 可用于选择最合适的函数重载 和模板专门化

此类需求的命名集称为概念。每个概念都是一个概念 谓词,在编译时求值,并成为 用作约束的模板的接口


请注意,此功能是在C++20中添加的,GCC只支持部分功能。

不,没有。模板是非常特别的。本质上,它们只是宏,其扩展由类型信息驱动。模板是否可以用给定类型实例化几乎完全是基于扩展定义的。事实上,只要不使用其他位,就允许实例化一个模板,这样只有其扩展的一部分会进行类型检查

扩展型检查是否依赖于C++的很多、许多特性、语法和语义。由于重载、隐式强制、强制类型转换和模板专业化等有问题的特性,不可能有参数属性提供免费的定理


一些评论提到了一些概念。然而,概念并没有改变这个属性——它们允许显式地对实例化进行约束,但与以前一样,没有这样的约束并不意味着它适用于所有情况。

模板不是一件正常的事情。它不能像一个编译一样,因为C++没有(并且可能永远不会)任何有意义的模板概念作为调用方和被调用方之间的接口和静态契约,就像函数的“向前声明”。想象一下,在一个世界中,任何函数实际上都是一个宏(几乎像可怕的
#define
样式,但不太坏),必须展开才能进行类型检查。这几乎就是模板

这也是模板如此强大的原因!模板形成图灵完备语言,因为模板实例可以递归。它是一种可怕的子语言,所以
constexpr
被发明出来,为递归编译时表达式提供了一种干净的子语言,而没有递归模板

您只能根据模板实例进行推理。“签名”什么也没告诉你。像干净的lisp宏一样,模板永远不会被正确地单独编译,即使使用“导出模板”也不行,因为“导出模板”需要在链接后再次运行编译器


顺便说一下,一个C++标准委员会成员暗示的想法是,“导出模板”被卖给C++专家,作为模板的一个适当的单独编译,就像它们是正常的非内联函数一样,是一个骗局;没有C++专家曾经相信过.

< p>这是C++中应该做的20个概念。当然,所有现有模板都是不受约束的(除非通过
enable_if
trickery或类似方法),因此明确使用
任何
概念可能有助于记录意图


<>这句话,C++没有参数多态性:没有一种方法来处理完全任意类型的“值”,因为没有指针指向引用。即使写<代码>()(代码)>对一个类型做出了不平凡的假设。因此,(草案)C++20标准库提供了“通用值”概念,这些概念实际上很有用,但提供的免费定理较少。

如果有人有更好的标题建议,特别是一些可以向没有听说过免费定理的人描述问题的内容,我很乐意更改。否。C++不保证你的模板函数与其他类型(除了你用它实例化的类型)一起工作。正是因为它可以使用实例化的类型的属性。java中的模板并不等同于C++。java是泛型(你操纵某种空洞*,容器不知道它包含的东西)。C++中的STD::列表甚至不是一个类型,STD::列表是一个。它不是泛型,而是关于模板(你在不同类型上应用同一个模板)。在C++中,容器与模板类型紧密相连,不同版本共享相同的概念和用法,但在C++中可能不是同一实现(在爪哇中不是这样的),它有特征类,它可以用于模板中,以支持类型支持的操作的要求。(C++ 20介绍(或拟引入)概念,它提供了一种更有效的方法。部分专业化。类型ID。特别重载。其中任何一种都单独排除了自由理论。概念的存在也不能保证任何类型或非类型的论点都会起作用。它说什么不应该尝试。是的,这就是我的意思。更抽象地说,concepts仅添加负信息