c++ - 从某个字符串文字和一个 int 模板参数的串联创建一个 constexpr C 字符串
问题描述
我有一个带有 int 模板参数的类。在某些情况下,我希望它输出错误消息。此消息应该是一些固定文本和模板参数的串联字符串。出于性能原因,我想避免在每次发生错误时在运行时构建这个字符串,理论上,字符串文字和模板参数在编译时都是已知的。所以我正在寻找一种可能性将其声明为 constexpr。
代码示例:
template<int size>
class MyClass
{
void onError()
{
// obviously won't work but expressing the concatenation like
// it would be done with a std::string for clarification
constexpr char errMsg[] = "Error in MyClass of size " + std::to_string (size) + ": Detailed error description\n";
outputErrorMessage (errMsg);
}
}
解决方案
使用static const
将只允许计算一次(但在运行时):
template<int size>
class MyClass
{
void onError()
{
static const std::string = "Error in MyClass of size "
+ std::to_string(size)
+ ": Detailed error description\n";
outputErrorMessage(errMsg);
}
};
如果您真的想在编译时拥有该字符串,您可以使用std::array
,例如:
template <std::size_t N>
constexpr std::size_t count_digit() {
if (N == 0) {
return 1;
}
std::size_t res = 0;
for (int i = N; i; i /= 10) {
++res;
}
return res;
}
template <std::size_t N>
constexpr auto to_char_array()
{
constexpr auto digit_count = count_digit<N>();
std::array<char, digit_count> res{};
auto n = N;
for (std::size_t i = 0; i != digit_count; ++i) {
res[digit_count - 1 - i] = static_cast<char>('0' + n % 10);
n /= 10;
}
return res;
}
template <std::size_t N>
constexpr std::array<char, N - 1> to_array(const char (&a)[N])
{
std::array<char, N - 1> res{};
for (std::size_t i = 0; i != N - 1; ++i) {
res[i] = a[i];
}
return res;
}
template <std::size_t ...Ns>
constexpr std::array<char, (Ns + ...)> concat(const std::array<char, Ns>&... as)
{
std::array<char, (Ns + ...)> res{};
std::size_t i = 0;
auto l = [&](const auto& a) { for (auto c : a) {res[i++] = c;} };
(l(as), ...);
return res;
}
最后:
template<int size>
class MyClass
{
public:
void onError()
{
constexpr auto errMsg = concat(to_array("Error in MyClass of size "),
to_char_array<size>(),
to_array(": Detailed error description\n"),
std::array<char, 1>{{0}});
std::cout << errMsg.data();
}
};
推荐阅读
- angularjs - 有没有办法在 md-colors 指令或 javascript 中获取主题的对比度默认颜色/字体颜色?
- azure-functions - Azure Functions:如何在本地开发环境中仅启动特定功能?
- python - 如何在 Kivy 中通过 id 正确链接按钮?
- python - 如何使用python将多个数据框中存在的一个特定列写入列表?
- python - 在数据框行的文本标签上创建成对相似度矩阵
- php - 为了保留彩色输出,我必须将 lynis 导出为什么格式?
- unity3d - MRTK“控制台”在构建时出现在一只眼睛中
- javascript - 如何用逗号而不是点对价格进行四舍五入?
- django - Django 保持签名两周或直到浏览器关闭
- reactjs - 如何在 React JS 中更改错误警报的位置