有没有办法避免 header 文件中使用的 constexpr 函数在没有额外命名空间的情况下进入全局范围?
Is there a way to avoid constexpr function used in header file from entering global scope without extra namespace for it?
我有一个 header 文件,其代码如下所示:
constexpr uint32 GenTag(const char tag[5]) { ... }
class SomeClass
{
static constexpr uint32 TAG1 = GenTag("smth");
static constexpr uint32 TAG2 = GenTag("abcd");
};
//constexpr needed for switch-case statement
问题是函数 GenTag()
属于全局范围,我想尽可能避免它。
我想在 class 中声明它,但在 constexpr
中是不可能的(此处解释:constexpr not working if the function is declared inside class scope)。
c++ 在 header 的末尾是否有类似 "undeclare" 的函数(也许是一些宏技巧)?或者我错过的任何其他选择?如果没有更好的方法,我可能会使用额外的(可能是过多的)命名空间,但想问问是否还有其他想法。
无法 "undeclare" C++ 中的函数或变量(头文件与否 -- 头文件仅包含在当前翻译单元中)。您需要使用命名空间,或将 GenTag
设为宏。您可以取消定义宏#undef MACRONAME
。
如何在继承的结构中将 GenTag()
定义为 static constexpr
方法?
如果您希望 GenTag()
仅在 SomeClass
内可用,您可以将其设为 private
并在 [=] 内将 SomeClass
定义为 friend
30=] 包含 GenTag()
.
我的意思是...如下
#include <iostream>
struct SomeClass;
class foo
{
static constexpr char GenTag(const char tag[5])
{ return tag[0]; }
friend SomeClass;
};
struct SomeClass : public foo
{
static constexpr char TAG1 = GenTag("smth");
static constexpr char TAG2 = GenTag("abcd");
};
int main()
{
std::cout << "Tag1: " << SomeClass::TAG1 << std::endl;
std::cout << "Tag2: " << SomeClass::TAG2 << std::endl;
// compilation error: 'GenTag' is a private member of 'foo'
// static constexpr char TAG3 = foo::GenTag("wxyz");
}
有了friend
技巧,就不需要继承foo
;但是,如果没有继承,您必须将其用作 foo::GetTag()
.
如果有人也遇到这样的问题,我建议您根本不要在 header 中使用此类 constexpr,而是考虑直接在 cpp 文件中且仅在 cpp 文件中使用 declare-define 它。那么你一定会避免不必要的全局范围污染。
或者,如果有多个地方可以使用这些常量,则在没有任何 classes 的情况下单独为它们创建一个单独的文件,并将该文件与包含 class 定义 header 分开.
我有一个 header 文件,其代码如下所示:
constexpr uint32 GenTag(const char tag[5]) { ... }
class SomeClass
{
static constexpr uint32 TAG1 = GenTag("smth");
static constexpr uint32 TAG2 = GenTag("abcd");
};
//constexpr needed for switch-case statement
问题是函数 GenTag()
属于全局范围,我想尽可能避免它。
我想在 class 中声明它,但在 constexpr
中是不可能的(此处解释:constexpr not working if the function is declared inside class scope)。
c++ 在 header 的末尾是否有类似 "undeclare" 的函数(也许是一些宏技巧)?或者我错过的任何其他选择?如果没有更好的方法,我可能会使用额外的(可能是过多的)命名空间,但想问问是否还有其他想法。
无法 "undeclare" C++ 中的函数或变量(头文件与否 -- 头文件仅包含在当前翻译单元中)。您需要使用命名空间,或将 GenTag
设为宏。您可以取消定义宏#undef MACRONAME
。
如何在继承的结构中将 GenTag()
定义为 static constexpr
方法?
如果您希望 GenTag()
仅在 SomeClass
内可用,您可以将其设为 private
并在 [=] 内将 SomeClass
定义为 friend
30=] 包含 GenTag()
.
我的意思是...如下
#include <iostream>
struct SomeClass;
class foo
{
static constexpr char GenTag(const char tag[5])
{ return tag[0]; }
friend SomeClass;
};
struct SomeClass : public foo
{
static constexpr char TAG1 = GenTag("smth");
static constexpr char TAG2 = GenTag("abcd");
};
int main()
{
std::cout << "Tag1: " << SomeClass::TAG1 << std::endl;
std::cout << "Tag2: " << SomeClass::TAG2 << std::endl;
// compilation error: 'GenTag' is a private member of 'foo'
// static constexpr char TAG3 = foo::GenTag("wxyz");
}
有了friend
技巧,就不需要继承foo
;但是,如果没有继承,您必须将其用作 foo::GetTag()
.
如果有人也遇到这样的问题,我建议您根本不要在 header 中使用此类 constexpr,而是考虑直接在 cpp 文件中且仅在 cpp 文件中使用 declare-define 它。那么你一定会避免不必要的全局范围污染。
或者,如果有多个地方可以使用这些常量,则在没有任何 classes 的情况下单独为它们创建一个单独的文件,并将该文件与包含 class 定义 header 分开.