7

为什么编译器没有为包含常量数据成员的类添加默认构造函数。请看下面的代码,因为我已经声明了常量数据成员'a',并且在尝试为类'ClassA'创建对象时,它说没有可用的适当的默认构造函数。请帮忙。

#include "stdafx.h"
#include <iostream>
using namespace std;

class ClassA
{
    private:
  const int a;
    public :
  void print()
  {
      cout << "hello world" << endl;
  }
};

int main()
{
  ClassA obj;
  obj.print();
  return 0;
}
4

5 回答 5

5

C++03 规则在 12.6.2/4 [class.base.init] 中指定。如果一个类的非静态成员没有在构造函数的成员初始化列表中被提及,那么如果它是const合格的,那么它必须是具有用户声明的构造函数的非 POD 类类型,否则程序将是 ill-形成。隐式定义的构造函数是用一个空的成员初始化器列表(和空的主体)定义的,因此在这种情况下,导致隐式声明的默认构造函数被隐式定义,它也会使程序格式错误。

C++11 规则相当于同样的事情。未在成员初始化器列表中指定的非静态数据成员被默认初始化。在 C++11 8.5/6 [dcl.init] 中,“[...] 如果程序要求对 const 限定类型的对象进行默认初始化TT则应是具有用户提供的默认构造函数的类类型。” 在这种情况下归结为相同的规则。

于 2013-05-23T06:58:46.903 回答
3

由于 const 值在初始化后无法更改,因此默认构造函数如何为其选择值。所以没有创建默认构造函数

于 2013-05-23T06:12:58.863 回答
2

由于a是一个const变量,因此可以将其声明为静态并对其进行初始化,而无需使用构造函数,如下所示,

class ClassA
{
    private:
    const static int a=10;
    public :
    void print()
    {
      cout << "hello world" << endl;
    }
};

int main()
{
  ClassA obj;
  obj.print();
  return 0;
}
于 2013-05-23T06:18:49.783 回答
1

该类型int在 C 或 C++ 中没有默认值,因此 的值a将是未定义的。例如,a如果在调试模式下运行,VC++ 将使用不同的默认值填充值,如果它在发布模式下运行。

在调试中,VC++使用以下值填充未初始化的内存:

  • 0xCCCCCCCC - 被微软的 C++ 调试运行时库和许多 DOS 环境用来标记未初始化的堆栈内存。
  • 0xCDCDCDCD - 由 Microsoft 的 C/C++ 调试 malloc() 函数用来标记未初始化的堆内存,通常从 HeapAlloc() 返回

因此,通过不初始化a您的程序,每次都会有不同的 const 值。

于 2013-05-23T06:31:58.357 回答
0

我相信你必须在构造函数中显式地初始化 const 成员,你必须在某个地方设置它们,因为它们是 const,你可以在任何你喜欢的地方设置它!

于 2013-05-23T06:14:12.787 回答