在编译时将 const char* 转换为 const char_type*
Convert const char* to const char_type* at compile time
考虑以下代码:
using char_type = /*implementation defined*/;
void foo(const char_type*);
int main()
{
foo("Hello World!");
}
字符串文字 "Hello World!"
是一个 const char*
,根据实现的不同,它可能无法转换为 const char_type*
。我希望我的代码可以在不同的实现之间移植,所以我想我可以定义一个文字来一个接一个地转换字符(这种类型的转换保证有效):
consteval const char_type* operator"" _s(const char*, size_t);
然后像这样使用它foo("Hello World!"_s)
。但是,我能想到的唯一实现是使用 new
来分配 space 和 std::copy
,但这会非常慢。我想在编译时进行转换,幸运的是我可以使用 c++20 和 consteval
关键字来确保对函数的调用总是产生一个常量表达式(用户定义的文字仍然是普通函数,它们可以在运行时被调用)。知道如何实现吗?
这种转换可以通过两步过程实现:首先,声明一个 class,它可以在编译时构造函数中将 const char *
转换为 char_type
数组;其次,通过在用户定义的文字中使用 class:
#include <algorithm>
template<std::size_t N>
struct string_convert {
char_type str[N] = {};
consteval string_convert(const char (&s)[N]) {
std::copy(s, s + N, str);
}
};
template<string_convert SC>
consteval auto operator ""_s()
{
return SC.str;
}
此界面允许以下用途:
void foo(const char_type *s);
foo("Hello, world!"_s);
试试看 on Godbolt。请注意,反汇编中既没有出现 string_convert
也没有出现用户定义的文字;剩下的就是转换后的数组。
考虑以下代码:
using char_type = /*implementation defined*/;
void foo(const char_type*);
int main()
{
foo("Hello World!");
}
字符串文字 "Hello World!"
是一个 const char*
,根据实现的不同,它可能无法转换为 const char_type*
。我希望我的代码可以在不同的实现之间移植,所以我想我可以定义一个文字来一个接一个地转换字符(这种类型的转换保证有效):
consteval const char_type* operator"" _s(const char*, size_t);
然后像这样使用它foo("Hello World!"_s)
。但是,我能想到的唯一实现是使用 new
来分配 space 和 std::copy
,但这会非常慢。我想在编译时进行转换,幸运的是我可以使用 c++20 和 consteval
关键字来确保对函数的调用总是产生一个常量表达式(用户定义的文字仍然是普通函数,它们可以在运行时被调用)。知道如何实现吗?
这种转换可以通过两步过程实现:首先,声明一个 class,它可以在编译时构造函数中将 const char *
转换为 char_type
数组;其次,通过在用户定义的文字中使用 class:
#include <algorithm>
template<std::size_t N>
struct string_convert {
char_type str[N] = {};
consteval string_convert(const char (&s)[N]) {
std::copy(s, s + N, str);
}
};
template<string_convert SC>
consteval auto operator ""_s()
{
return SC.str;
}
此界面允许以下用途:
void foo(const char_type *s);
foo("Hello, world!"_s);
试试看 on Godbolt。请注意,反汇编中既没有出现 string_convert
也没有出现用户定义的文字;剩下的就是转换后的数组。