gpt4 book ai didi

c++ - 在编译时初始化非常大的 C++ std::bitset

转载 作者:行者123 更新时间:2023-12-04 03:34:00 31 4
gpt4 key购买 nike

我想存储一个 216 位的静态常量位集,其中 1 和 0 的特定序列永远不会改变。

我想到了使用 this post 提出的初始化字符串:

std::bitset<1<<16> myBitset("101100101000110 ... "); // the ellipsis are replaced by the actual 65536-character sequence

但是编译器 (VS2013) 给了我 "string too long"错误。

更新

我尝试按照上面链接的帖子中的建议将字符串拆分成更小的 block ,如下所示:

std::bitset<1<<16> myBitset("100101 ..."
"011001 ..."
...
);

但我收到错误 C1091:编译器限制:字符串长度超过 65535 字节。我的字符串是 65536 字节(技术上是 65537,带有 EOS 字符)。

我还有哪些其他选择?

更新

感谢luk32 ,这是我最终得到的漂亮代码:

const std::bitset<1<<16> bs = (std::bitset<1<<16>("101011...")
<< 7* (1<<13)) | (std::bitset<1<<16>("110011...")
<< 6* (1<<13)) | (std::bitset<1<<16>("101111...")
<< 5* (1<<13)) | (std::bitset<1<<16>("110110...")
<< 4* (1<<13)) | (std::bitset<1<<16>("011011...")
<< 3* (1<<13)) | (std::bitset<1<<16>("111011...")
<< 2* (1<<13)) | (std::bitset<1<<16>("111001...")
<< 1* (1<<13)) | std::bitset<1<<16>("1100111...");

最佳答案

您并没有真正拆分文字。无论如何,它都会被连接起来进行编译。您受到编译器的限制。我认为没有办法在 MSVC 中增加此限制。

您可以将其拆分为两个文字,初始化两个位集,移位第 1 部分和 OR与另一个。

类似于:

#include <iostream>
#include <string>
#include <bitset>


using namespace std;
int main()
{
std::bitset<8> dest("0110");
std::bitset<8> lowBits("1001");

dest <<= dest.size()/2;
dest |= lowBits;
std::cout << dest << '\n';
}

如果您查看 clang compiler output at -02 , 它被优化以加载 105这是 01101001 .

我的测试表明,如果你交换 8对于 1<<16它使用 SSE,所以它应该是非常安全的赌注。它没有像 8 那样丢弃文字或 16 ,因此可能会有一些运行时开销,但我不确定您是否可以做得更好。

编辑:

我做了更多测试,这里是 my playground :

#include <iostream>
#include <string>
#include <bitset>


using namespace std;
int main()
{
//static const std::bitset<16> set1( "01100110011001100110011001100110");
static const std::bitset<16> set2(0b01100110011001100110011001100110);

static const std::bitset<16> high(0b01100110);
static const std::bitset<16> low (0b01100110);
static const std::bitset<16> set3 = (high << 8) | low;
std::cout << (set3 == set2) << '\n';
}

我无法获得 const char* 的编译时优化除 clang 之外的任何编译器上的构造函数,最多可使用 14 个字符。 s 从 bitset 初始化并将它们移动并组合在一起:

static const std::bitset<128> high(0b0110011001100110011001100110011001100110011001100110011001100110);
static const std::bitset<128> low (0b1001100110011001100110011001100110011001100110011001100110011001);
static const std::bitset<128> set3 = (high << high.size()/2) | low;
std::cout << set3 << '\n';

这使得编译器坚持使用二进制数据存储。如果可以使用更新一点的编译器 unsigned long long我认为可以将其声明为 constexpr 的数组由 bitset 构建s 并用 ull 将它们连接起来函数并绑定(bind)到 constexpr变量,这应该确保可能的最佳优化。编译器仍然可能不利于你,但没有理由。甚至可能没有 constexpr const它将生成非常优化的代码。

关于c++ - 在编译时初始化非常大的 C++ std::bitset,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67298395/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com