Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/160.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
类声明或定义中的静态变量? 我是C++新手。 我有一门课是这样的: class CodeTest { private: static const int TOTAL=100; };_C++_Static Members - Fatal编程技术网

类声明或定义中的静态变量? 我是C++新手。 我有一门课是这样的: class CodeTest { private: static const int TOTAL=100; };

类声明或定义中的静态变量? 我是C++新手。 我有一门课是这样的: class CodeTest { private: static const int TOTAL=100; };,c++,static-members,C++,Static Members,TOTAL是声明还是定义 当我阅读Scott Meyer的书时,有人提到在实现文件中,我们需要定义如下内容: const int CodeTest::TOTAL; 为什么需要这样做?需要在头之外的实现文件中进行声明,因为否则包含此头的每个翻译单元都将定义自己的对象(即,它自己的变量存储) 这将违反法律。结果可能是,如果变量在一个翻译单位中发生了变化,那么其他翻译单位将看不到这种变化。现在,这没有那么重要,因为变量是常量。然而,接受它的地址也会在不同的翻译单位中产生不同的指针。问题的第一部分:

TOTAL
是声明还是定义

当我阅读Scott Meyer的书时,有人提到在实现文件中,我们需要定义如下内容:

const int CodeTest::TOTAL;

为什么需要这样做?

需要在头之外的实现文件中进行声明,因为否则包含此头的每个翻译单元都将定义自己的对象(即,它自己的变量存储)


这将违反法律。结果可能是,如果变量在一个翻译单位中发生了变化,那么其他翻译单位将看不到这种变化。现在,这没有那么重要,因为变量是常量。然而,接受它的地址也会在不同的翻译单位中产生不同的指针。

问题的第一部分:

此行:
static const int TOTAL=100是一个声明,后跟一个初始化

TOTAL
是一个标识符

问题的第二部分


const int CodeTest::TOTAL
是初始化变量所必需的。

由于这引发了一些争议,我查看了标准,而@Nawaz是对的,我错了

9.4.2/2

如果
静态
数据成员是常量整型[…]。成员 如果在中使用,则仍应在命名空间范围中定义 程序和命名空间范围定义不应包含 初始化器

这里有一个声明,变量被初始化为一个值。在类之外,必须定义变量,但不能为其赋值

具有
const
integral类型的部分仅适用于此特定情况-即,您可以在类内初始化所述类型,但所有
静态
数据成员必须在类外定义

要回答这个问题: 无论定义在类外部是否是必需的(取决于是否使用成员),类内部的任何内容(初始化与否)都只是一个声明

static const int TOTAL=100; // is a declaration followed by an initialisation.

从C++标准3.1节:

声明将名称引入翻译单元,或重新声明先前声明引入的名称。声明指定这些名称的解释和属性

下一段说明声明是一个定义,除非。。。。。。它在类定义中声明静态成员:

struct X
{
    int a;         // defines a
    static int b;  // declares b
};

您可以在此处阅读有关定义和声明的更多信息:

此处有必要输入:@Griwes完全没有帮助。“这是一个很好的问题。”科拉德鲁道夫,每一本像样的书都解释得很好。来吧。@Griwes祝贺你。您刚刚解释了为什么堆栈溢出是完全不必要的。买书就行了。FWW,我花了很长时间才明白这一点,即使阅读了很多(好的和坏的)C++书籍来解释TU是如何工作的。+ 1在一个美丽的星期日下午引起了争论。code>在类外,必须定义变量
,只有在需要该静态变量地址的情况下才必须,否则,您不需要定义它:P@Mr.Anubis如果你不想要有效的C++,你是对的。然而,标准是这样说的。。。(如果你使用它,不仅仅是它的地址)@Mr.Anubis,这还不清楚。关于吕钦引用的段落中“使用”的含义存在相当大的争议。因此,对C++11的措辞进行了修改,以使其更加清晰。对,唯一的问题是,为什么Stroustrup说您可以使用它们而不需要记录地址。@KonradRudolph说的话和他引用的内容有差异:/您的回答没有意义,因为成员函数可以在类本身内部定义,那为什么不是静态成员呢?正如我所说的,完美的答案是,因为标准是这样说的。而且因为R Marthino在聊天中提到了这一点:可以在每个TU中使用静态存储定义一个单独的实例,但这不是我们想要的(通常)!我们希望从所有TU访问一个实例。@Nawaz但这些函数定义为
内联的
,所以这不是一回事。@Nawaz成员函数是完全不同的,它们是内联的。见我之前的评论,这有点相关。C++也可以为静态模板类模板做同样的操作,但是这又会创建不同的对象。@ Nawaz Nooooo!代码>内联不是编译器的提示,它决定了链接。是的,就实际内联而言,这是一个提示,但它也决定了链接,这样的函数不会被导出,因此也不会违反ODR。我认为仅仅说“是”或“否”并不是真正的建设性的。TOTAL不是一个变量,正如前面的
const
word标记的那样。它是一个常量,它被视为任何常量定义,并且允许编译器在数据区域中为它分配空间。