考虑以下代码:
template <class Derived>
class KFBase
{
public:
template <typename Nom>
struct State {
Nom nominal_state;
};
};
template <typename A>
class PFilter
: public KFBase<PFilter<A>>
{
public:
using Base = KFBase<PFilter<A>>;
// comment this out and it works
using State = typename Base::State<int>;
};
int main(int, char**){
PFilter<int>{};
}
正如评论中所暗示的,如果我注释掉 State 别名,一切都可以在 MSVC 上正常编译。但是,如果我包含它,则在使用 C++17 或 C++20 编译时会出现编译错误(https://godbolt.org/z/aM78ToMsc),但回滚到 C++14 时它可以工作再次在 MSVC 上 (https://godbolt.org/z/Eej9bjrf7)
在 GCC 上,它可以与 C++20 一起编译,所以我想知道我是否遵循 C++ 标准,或者这是 C++17 MSVC 实现中引入的错误。
我的直觉是这与 CTAD 有关,但我不确定。
有谁能解释一下吗?
附注 如果有人对这个问题有更好的标题,请告诉我。
您可能需要
template
来表明 <
不是比较
using State = typename Base::template State<int>;
MSVC 在 C++14 模式下相当宽松(因为当时确实如此)。更高版本默认打开
/permissive-
标志。
也许 gcc 默认也有更宽松的模式,我不知道。