Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/161.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++ 仅头文件中的静态常量整型类成员-正确的方法?_C++_Static_Constants_Member - Fatal编程技术网

C++ 仅头文件中的静态常量整型类成员-正确的方法?

C++ 仅头文件中的静态常量整型类成员-正确的方法?,c++,static,constants,member,C++,Static,Constants,Member,假设我有以下例子: #include <cstdlib> class A { public: static const std::size_t value = 42; }; 但是,我不能这样做,因为我希望此文件仅为头文件。另一个常见的解决方案是: class A { public: enum { value = 42 }; }; 我也不喜欢这个解决方案,因为我希望A::value的类型是std::size\t 解决这个问题的好办法是什么?最好是小型便携式解决方案

假设我有以下例子:

#include <cstdlib>

class A {
public:
    static const std::size_t value = 42;
};
但是,我不能这样做,因为我希望此文件仅为头文件。另一个常见的解决方案是:

class A {
public:
    enum { value = 42 };
};
我也不喜欢这个解决方案,因为我希望
A::value
的类型是
std::size\t

解决这个问题的好办法是什么?最好是小型便携式解决方案,而不是像
BOOST\u STATIC\u CONSTANT
这样具有巨大宏魔力的解决方案



我想要的是C++03的解决方案,而不是C++11(在这里很简单)。

首先,使用无符号的
size\t
类型表示数字,可能会遇到隐式升级问题。因此,最好使用其相应的有符号类型,即
ptrdiff\u t
。它恰好是指针差异表达式的结果类型

此外,由于C++11中的更改,通常最好包括
而不是
,即编写
::ptrdiff_t
或只是简单的
ptrdiff_t
,而不是
std::ptrdiff_t

现在,下面是如何执行头文件外部链接常量的操作:

template< class Dummy >
struct A_constants_
{
    static ::ptrdiff_t const value;
};

template< class Dummy >
::ptrdiff_t const A_constants_<Dummy>::value = 42;

typedef A_constants_<void> A_constants;

class A
    : public A_constants
{
public:
    // Whatever
};

还有其他一些方法可以做到这一点,但上面的方法是最简单、最容易做到的。

在第二种情况下,使用C++11编译器,您可以使用
enum类enum_name:std::size_t{value=42}
为了确保类型是std::size_t@Prætorian-是的,如果你有C++11。对不起,我这里说的是C++03,让我补充一下。@Prætorian-如果你必须删除它,但我认为一点幽默是值得的。你介意解释一下为什么这样做吗?这是否意味着每个编译单元都包含了它自己的代码<代码:A::值< /C>(有一个唯一的地址)?@ NealCurk:ActualCurror:它是有效的,因为C++标准的ODR(一个定义规则)对模板类中的常量有特殊的豁免,因为提供C++模板代码的唯一实用方法是在头文件中。这意味着,如果访问该地址,则在所有转换单元中,常数的地址都保证相同。然而,编译器一如既往地可以根据“仿佛”规则进行自由优化,这意味着不能保证值不会被复制,从而占用“不必要”的空间。除了据我所知,这需要一个不寻常的编译器来完成。@Cheersandhth.-Alf我知道已经很晚了,但是你能解释一下吗,由于C++11的变化,一般来说,包含和不包含是一个好主意,即write::ptrdiff_t或只是简单的ptrdiff_t,而不是std::ptrdiff_t?也许是作为一个编辑或在你的博客?谢谢。@Koushik:昨天有人发表了评论,所以,随信附上。:-)@干杯-阿尔夫,非常感谢。你的回答真的帮了我的忙。:-)
template< class Dummy >
struct A_constants_
{
    static ::ptrdiff_t const value;
};

template< class Dummy >
::ptrdiff_t const A_constants_<Dummy>::value = 42;

typedef A_constants_<void> A_constants;

class A
    : public A_constants
{
public:
    // Whatever
};
foo( A::value );