Ale*_*kiy 5 c++ gcc templates language-lawyer
这段代码在gcc6中导致错误(但在gcc 4.8、5.2和clang 3.6中可以正常工作):
template <typename T>
struct outer
{
template <typename U>
struct inner
{
};
};
template <typename T>
struct is_inner_for
{
template <typename Whatever>
struct predicate
{
static constexpr bool value = false;
};
template <typename U>
struct predicate<typename outer<T>::template inner<U>>
{
static constexpr bool value = true;
};
};
static_assert(
is_inner_for<int>::template predicate<
outer<int>::inner<double>
>::value,
"Yay!"
);
Run Code Online (Sandbox Code Playgroud)
错误是:
main.cpp:22:9: error: template parameters not deducible in partial specialization:
struct predicate<typename outer<T>::template inner<U>> : std::true_type
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
main.cpp:22:9: note: 'U'
^~~~~~~~~~~~~
Run Code Online (Sandbox Code Playgroud)
命令行是:
g++ -std=c++1y -c main.cpp
Run Code Online (Sandbox Code Playgroud)
我已经在这里向gcc提交了错误报告:https://gcc.gnu.org/bugzilla/show_bug.cgi? id = 70141
但是,它被标记为无效(我认为是错误的)。outer<T>内部使用的当时是predicate一种具体类型,因此它不是非推论上下文。
标准中是否有任何阻止它成为有效C ++代码的内容?
我怀疑这是 gcc 6.0 中的一个错误,以及 clang 3.9 中的错误警告(该警告很奇怪 - 因为该警告意味着不会选择部分专业化,但如果不选择它,则会触发静态断言)。
\n\n来自[temp.class.spec.match]:
\n\n\n\n\n如果可以从实际模板参数列表推导出部分特化的模板参数,则部分特化与给定的实际模板参数列表匹配\n
\n
我们可以从U中推导出来吗?typename outer<T>::template inner<U>outer<int>::inner<double>
来自 [temp.deduct.type]:
\n\n\n\n\n如果模板参数仅在非推导上下文中使用并且未显式指定,则模板参数推导将失败。
\n\n非推导的上下文是:
\n
\n \xe2\x80\x94使用Qualified-id指定的类型的嵌套名称说明符。\n \xe2\x80\x94 [...]
但这里指定的嵌套名称typename outer<T>是,它不包含我们试图推断的类型。其他非推导上下文均不适用。所以这里推演应该成功。
考虑以下等效情况:
\n\n#include <utility>\n\ntemplate <class >\nstruct outer\n{\n template <class U> struct inner {};\n};\n\ntemplate <class T>\nstruct bar {\n template <class U> std::false_type foo(U const&);\n template <class U> std::true_type foo(typename outer<T>::template inner<U> const&);\n};\n\n\nint main() {\n static_assert(decltype(bar<int>{}.foo(outer<int>::inner<double>{}))::value, "!");\n}\nRun Code Online (Sandbox Code Playgroud)\n\ngcc 6.0 和 clang 3.9 都会在没有警告的情况下编译此代码 - 但这与原始示例中的部分特化中发生的推论是相同的。
\n| 归档时间: |
|
| 查看次数: |
2329 次 |
| 最近记录: |