为什么 const 成员可以被初始化两次?
Why could const member be initialized twice?
下面是一个代码片段,可以在vs2015
中编译并且运行没有错误
#include<iostream>
using namespace std;
class A {
public:
A(int b) :k(b) {}//second time
const int k = 666;//first time
};
int main() {
A a(555);
cout << a.k << endl;
return 0;
}
输出为555
。但据我所知,const
对象应该只初始化一次,之后该值是不可修改的。
没有初始化两次; default member initializer 只是被忽略了。所以对于A a(555);
,a.k
被初始化为555
.
If a member has a default member initializer and also appears in the member initialization list in a constructor, the default member initializer is ignored.
根据标准,[class.base.init]/10:
If a given non-static data member has both a default member
initializer and a mem-initializer, the initialization specified by the
mem-initializer is performed, and the non-static data member's default
member initializer is ignored. [ Example: Given
struct A {
int i = /* some integer expression with side effects */ ;
A(int arg) : i(arg) { }
// ...
};
the A(int)
constructor will simply initialize i
to the value of arg
,
and the side effects in i
's default member initializer will not take
place. — end example ]
另一方面,给定
class A {
public:
A() {} // k will be initialized via default member initializer, i.e. 666
A(int b) :k(b) {} // k will be initialized via member initializer list, i.e. b
const int k = 666;
};
那么对于A a;
,a.k
将被初始化为666
。
只初始化一次
const int k = 666;
如果在构造函数中没有提供,将被使用。
下面是一个代码片段,可以在vs2015
中编译并且运行没有错误#include<iostream>
using namespace std;
class A {
public:
A(int b) :k(b) {}//second time
const int k = 666;//first time
};
int main() {
A a(555);
cout << a.k << endl;
return 0;
}
输出为555
。但据我所知,const
对象应该只初始化一次,之后该值是不可修改的。
没有初始化两次; default member initializer 只是被忽略了。所以对于A a(555);
,a.k
被初始化为555
.
If a member has a default member initializer and also appears in the member initialization list in a constructor, the default member initializer is ignored.
根据标准,[class.base.init]/10:
If a given non-static data member has both a default member initializer and a mem-initializer, the initialization specified by the mem-initializer is performed, and the non-static data member's default member initializer is ignored. [ Example: Given
struct A { int i = /* some integer expression with side effects */ ; A(int arg) : i(arg) { } // ... };
the
A(int)
constructor will simply initializei
to the value ofarg
, and the side effects ini
's default member initializer will not take place. — end example ]
另一方面,给定
class A {
public:
A() {} // k will be initialized via default member initializer, i.e. 666
A(int b) :k(b) {} // k will be initialized via member initializer list, i.e. b
const int k = 666;
};
那么对于A a;
,a.k
将被初始化为666
。
只初始化一次
const int k = 666;
如果在构造函数中没有提供,将被使用。