c++ - 在运行时使用模板化的 constexpr

标签 c++ constexpr

我喜欢这个 crc32 实现:CygnusX1 CRC32

它在编译时运行良好:

ctcrc32("StackOverflow");

但是否可以在运行时使用它:

void myfunction(const std::string& str)
{
  uint32_t hash = ctcrc32(str);
  // ...
}

到目前为止,我不得不重写另一个(运行时)函数,但我更愿意只使用一个。

编辑

我试过

ctcrc32(str.c_str()) 

但它不起作用(**不匹配的类型‘const char [len]’和‘const char*’**)。它似乎需要一个编译时间长度。


实现如下:

namespace detail {
// CRC32 Table (zlib polynomial)
static constexpr uint32_t crc_table[256] = { 0x00000000L, 0x77073096L, ... }

template<size_t idx>
constexpr uint32_t combine_crc32(const char * str, uint32_t part) {
  return (part >> 8) ^ crc_table[(part ^ str[idx]) & 0x000000FF];
}

template<size_t idx>
constexpr uint32_t crc32(const char * str) {
  return combine_crc32<idx>(str, crc32<idx - 1>(str));
}

// This is the stop-recursion function
template<>
constexpr uint32_t crc32<size_t(-1)>(const char * str) {
  return 0xFFFFFFFF;
}

} //namespace detail

template <size_t len>
constexpr uint32_t ctcrc32(const char (&str)[len]) {
  return detail::crc32<len - 2>(str) ^ 0xFFFFFFFF;
}

最佳答案

您不能将它与 std::string 一起使用无需重写。如果您查看主要功能:

template <size_t len>
constexpr uint32_t ctcrc32(const char (&str)[len]) {
  return detail::crc32<len - 2>(str) ^ 0xFFFFFFFF;
}

...您会看到它在编译时需要字符串的长度,因为它将它用作模板参数 ( detail::crc32<len - 2>)。

ctcrc32仅适用于编译时已知大小的字符数组(它们不必是 constconstexpr ,但大小必须已知)。

我根据允许编译时和运行时字符串的链接问题的原始实现写了一个答案:

https://stackoverflow.com/a/48924267/2666289

关于c++ - 在运行时使用模板化的 constexpr,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48923259/

相关文章:

c++ - 从另一个文件编译 __device__ 函数调用时出现 Visual Studio MSB3721 错误

c++ - 为什么使用 GetModuleHandle 获取基地址有效?

c++ - `static constexpr` 在常量表达式中调用的函数是...错误?

c++ - 必须预先定义 constexpr 函数?

c++ - 为什么 for-loop 不是编译时表达式并且扩展的 constexpr 允许在 constexpr 函数中进行循环

c++ - GetRawInputData 与 GetAsyncKeyState()

c++ - 可变参数模板参数的模板类型数组

c++ - if else 语句和字符串长度之间的代码性能

c++ - 使用 C++ constexpr 对 N 位字进行位反转

c++ - 为什么要使用 constexpr