Fur*_*ish 5 c++ templates language-lawyer
知道我们必须在哪里以及为什么要放置templateandtypename关键字后,我惊讶地发现 MSVC接受以下代码:
struct foo {
using bar = int;
};
template <typename T>
void quux() {
T::template bar b;
}
int main() {
quux<foo>();
}
Run Code Online (Sandbox Code Playgroud)
根据我的理解, 的用法T::template bar b;是不正确的。声明的正确方法b是使用typename,如下所示:(typename T::bar b;而不是T::template bar b;)。template将意味着这bar是一个模板,但事实并非如此。
它是 MSVC 中的错误导致它接受不正确的代码,还是标准允许它并且 Clang 和 GCC 都没有以这种方式实现它(因此需要正确使用typename此处)?
MSVC 有一个长期存在的错误 - 当我询问您链接的模板类型名称问题时,它已经是一个老错误了。简而言之,自 1998 年以来,C++ 要求在模板中进行两阶段名称查找。在第一阶段,当编译模板本身时,仅查找不依赖的名称,因为尚不知道实际的模板参数。在第二阶段,查找依赖名称(有关详细信息,请参阅链接的问题)。
但MSVC不会这样做,而是在实例化模板时进行所有查找。在您的情况下,这意味着所有查找都在 MSVC 编译时完成quux<foo>,而在编译时则不执行任何操作quux<T>。由于它不执行第一阶段,因此它不需要typename依赖名称。MSVC 已经了解quux::b.
看来 MSVC 走得更远一些。它不仅忽略了正确的typename,而且还忽略了template本示例中错误使用的 as 。当忽略一些事情时,这并不完全令人惊讶。
| 归档时间: |
|
| 查看次数: |
93 次 |
| 最近记录: |