我想有一个类的私有静态常量(在这种情况下是一个形状工厂)。
我想要这样的东西。
class A {
private:
static const string RECTANGLE = "rectangle";
}
不幸的是,我从c++ (g++)编译器得到了各种各样的错误,比如:
ISO c++禁止初始化
“矩形”成员
非整型静态数据成员' std::string '的类内初始化无效
错误:使“矩形”静态
这说明这种构件设计是不符合标准的。如何在不使用#define指令的情况下获得私有文字常量(或者公共常量)(我想避免数据全局的丑陋!)
任何帮助都是感激的。
类静态变量可以在头文件中声明,但必须在.cpp文件中定义。这是因为一个静态变量只能有一个实例,而编译器无法决定将它放在哪个生成的对象文件中,所以你必须做出决定。
将静态值的定义与c++ 11中的声明保持一致
可以使用嵌套的静态结构。在本例中是static成员
是一个结构,必须在.cpp文件中定义,但值
都在头文件中。
class A
{
private:
static struct _Shapes {
const std::string RECTANGLE {"rectangle"};
const std::string CIRCLE {"circle"};
} shape;
};
不是初始化单个成员,而是在.cpp中初始化整个静态结构:
A::_Shapes A::shape;
访问这些值
A::shape.RECTANGLE;
或者——因为成员是私有的,只能从A - with中使用
shape.RECTANGLE;
注意,这个解决方案仍然受到的顺序问题的影响
静态变量的初始化。当使用静态值时
初始化另一个静态变量,第一个可能没有初始化,
然而。
// file.h
class File {
public:
static struct _Extensions {
const std::string h{ ".h" };
const std::string hpp{ ".hpp" };
const std::string c{ ".c" };
const std::string cpp{ ".cpp" };
} extension;
};
// file.cpp
File::_Extensions File::extension;
// module.cpp
static std::set<std::string> headers{ File::extension.h, File::extension.hpp };
在这种情况下,静态变量头将包含{""}
或{".h", ".hpp"},这取决于链接器创建的初始化顺序。
正如@abyss提到的。7如果变量的值可以在编译时计算,你也可以使用constexpr。但是如果你用静态constexpr const char*声明你的字符串,并且你的程序使用std::string,否则就会有开销,因为每次你使用这样的常量都会创建一个新的std::string对象:
class A {
public:
static constexpr const char* STRING = "some value";
};
void foo(const std::string& bar);
int main() {
foo(A::STRING); // a new std::string is constructed and destroyed.
}
你必须在类定义之外定义你的静态成员,并在那里提供初始化式。
第一个
// In a header file (if it is in a header file in your case)
class A {
private:
static const string RECTANGLE;
};
然后
// In one of the implementation files
const string A::RECTANGLE = "rectangle";
您最初尝试使用的语法(类定义中的初始化式)只允许整型和枚举类型。
从c++ 17开始,你有另一个选项,这与你最初的声明非常相似:内联变量
// In a header file (if it is in a header file in your case)
class A {
private:
inline static const string RECTANGLE = "rectangle";
};
不需要额外的定义。