c++ - 错误 C2327 : not a type name, 静态或枚举数

标签 c++ windows visual-studio templates g++

我在 Windows 上遇到“错误 C2327”。
我减少了我的代码并在测试程序中遇到了类似的错误

#include <boost/intrusive/list.hpp>
#include <iostream>

class Test {
protected:
         typedef Test self_type;
         boost::intrusive::list_member_hook<> order_hook;
public:
         typedef boost::intrusive::member_hook<self_type,
                            boost::intrusive::list_member_hook<>,
                            & Test::order_hook > order_hook_type;
};

这在 g++ 上工作正常,但在 Windows 上它给出以下错误:

test.cpp(11) : error C2327: 'Test::order_hook' : is not a type name, static, or enumerator
test.cpp(11) : error C2065: 'order_hook' : undeclared identifier

请帮忙。 Windows 缺少什么?

最佳答案

tl;dr:Visual Studio 是正确的 — 您不能将 typedef 放在那里。
Boost 文档 gets this right, but doesn't explain why .


[C++11: 14.3.2/1]: A template-argument for a non-type, non-template template-parameter shall be one of:

  • for a non-type template-parameter of integral or enumeration type, a converted constant expression (5.19) of the type of the template-parameter; or
  • the name of a non-type template-parameter; or
  • a constant expression (5.19) that designates the address of an object with static storage duration and external or internal linkage or a function with external or internal linkage, including function templates and function template-ids but excluding non-static class members, expressed (ignoring parentheses) as & id-expression, except that the & may be omitted if the name refers to a function or array and shall be omitted if the corresponding template-parameter is a reference; or
  • a constant expression that evaluates to a null pointer value (4.10); or
  • a constant expression that evaluates to a null member pointer value (4.11); or
  • a pointer to member expressed as described in 5.3.1.

[C++11: 5.3.1/3]: The result of the unary & operator is a pointer to its operand. The operand shall be an lvalue or a qualified-id. If the operand is a qualified-id naming a non-static member m of some class C with type T, the result has type “pointer to member of class C of type T” and is a prvalue designating C::m. [..]

[C++11: 8.3.3/2] 给出了一个不完整类型的指向成员的示例,只要指向成员的指针不是实际上已初始化,虽然没有明确说明,但其含义是要实际获取某些 C::m 的地址,C 必须是完整类型。事实上,直到 C 是一个完整的类型,C::m 才真正存在。

有一些类似的规则更清晰:

[C++11: 9.2/10]: Non-static (9.4) data members shall not have incomplete types. In particular, a class C shall not contain a non-static member of class C, but it can contain a pointer or reference to an object of class C.

在你的 typedef 点,Test 不是一个完整的类型:

[C++11: 9.2/2]: A class is considered a completely-defined object type (3.9) (or complete type) at the closing } of the class-specifier. Within the class member-specification, the class is regarded as complete within function bodies, default arguments, exception-specifications, and brace-or-equal-initializers for non-static data members (including such things in nested classes). Otherwise it is regarded as incomplete within its own class member-specification.

因此,您不能在该位置使用指向成员的指针。您必须编写 typedef,使其出现在类定义的结束 } 之后,或者使指向的对象成为非成员对象,或者 static 成员。

海湾合作委员会 must have a bug or extension in this regard ,因为以下测试用例编译并成功执行:

template <typename B, int B::* PTM>
struct A {};
 
struct B
{
    int x;
 
    typedef A<B, &B::x> a;
};
 
int main() {
    B b;
}

而 Visual Studio 2012 Express 正确输出:

1>------ Build started: Project: test1, Configuration: Debug Win32 ------
1> test.cpp
1>f:\documents\visual studio 2012\projects\test1\test1\test.cpp(8): error C2327: 'B::x' : is not a type name, static, or enumerator
1>f:\documents\visual studio 2012\projects\test1\test1\test.cpp(8): error C2065: 'x' : undeclared identifier
1>f:\documents\visual studio 2012\projects\test1\test1\test.cpp(8): error C2975: 'PTM' : invalid template argument for 'A', expected compile-time constant expression
1> f:\documents\visual studio 2012\projects\test1\test1\test.cpp(1) : see declaration of 'PTM'
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========

关于c++ - 错误 C2327 : not a type name, 静态或枚举数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19564009/

相关文章:

c++ - 在哪里可以找到 MS Office 界面以在 C++ 和 COM 中进行一些自动化

c++ - 遍历 multiset 元素的所有组合

windows - 最近更新到 Windows 10 后,VMWare Workstation 无法在 Windows 10 上运行

windows - 如何递归地将特定模式的文件复制到 Windows 上的单个平面文件夹中?

visual-studio - 用于科学计算的 Qt 与 Visual Studio

c++ - 使用 opencv mog 检测器和 c++ 从实时摄像机馈送中进行背景减法

编译给出与 Windows 编译器不同的结果

c# - VS 2008——在构建属性中使用相对路径

visual-studio - 如何使用键盘快捷键浏览智能感知建议?

c++ - 取消分配数组中的项目