在静态变量的构造函数中检索静态 const 变量的值
我知道下面的代码会导致分段错误,因为在 A 的 cstr 处,B::SYMBOL 尚未初始化。但为什么?
实际上,A 是一个对象,用作将 B 等类的 SYMBOL 映射到它们各自的 ID 的映射。 C 静态保存此映射(A),以便它可以将映射提供为类函数。
A 的主要功能是充当 C 的映射,在启动时初始化自身。如果我仍然可以在代码中使用 B::ID 和 B::SYMBOL (没有 #define pls),我应该如何在没有分段错误的情况下做到这一点?
(ps.假设我已经实现了包含守卫)
//A.h
#include "B.h"
class A
{
public:
A()
{
std::cout<<B::ID<<std::endl;
std::cout<<B::SYMBOL<<std::endl;
}
};
//B.h
class B
{
public:
static const int ID;
static const std::string SYMBOL;
}
//B.cpp
#include "B.h"
const int B::ID = 1;
const std::string B::SYMBOL = "B";
//C.h
#include "A.h"
class C
{
public:
static A s_A;
};
//C.cpp
#include "C.h"
A C::s_A;
//main.cpp
#include "C.h"
int main(int c, char** p)
{
}
I understand that the code below would result segmentation fault because at the cstr of A, B::SYMBOL was not initialized yet. But why?
In reality, A is an object that serves as a map that maps the SYMBOLs of classes like B to their respective IDs. C holds this map(A) static-ly such that it can provide the mapping as a class function.
The primary function of A is to serve as a map for C that initializes itself at startup. How should I be able to do that without segmentation fault, provided that I can still use B::ID and B::SYMBOL in the code (no #define pls)?
(ps. assume I have implemented the include guards)
//A.h
#include "B.h"
class A
{
public:
A()
{
std::cout<<B::ID<<std::endl;
std::cout<<B::SYMBOL<<std::endl;
}
};
//B.h
class B
{
public:
static const int ID;
static const std::string SYMBOL;
}
//B.cpp
#include "B.h"
const int B::ID = 1;
const std::string B::SYMBOL = "B";
//C.h
#include "A.h"
class C
{
public:
static A s_A;
};
//C.cpp
#include "C.h"
A C::s_A;
//main.cpp
#include "C.h"
int main(int c, char** p)
{
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

发布评论
评论(2)
您所说的分段错误是什么?您的代码根本无法编译,因为 B
的成员(以及 B
本身)在 A::A() 之前没有声明
。编译器根本不知道B
是什么。
如果交换 A
和 B
的定义,那么代码应该可以编译并正常工作。只要所有内容都在同一个翻译单元中,初始化顺序就不会有任何问题,假设 B
的静态成员的定义位于 B
之前C::s_A
的 em>定义。在同一翻译单元中定义的对象按照其定义的顺序进行初始化,这意味着在 A::A()
启动时,B
的静态成员已经初始化。在这种情况下,不存在出现分段错误的可能性。
如果您遇到分段错误,则必须采取不同的措施。定义顺序不同?也许有多个翻译单元?发布/描述真实的代码。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
使用 s_A 的延迟初始化。这可能有效:
或者:
这两种解决方案都不是线程安全的。
Use lazy initialization of s_A. This might work:
Or:
Neither solution is thread safe.