我有一个算法,我目前使用两个无符号整数作为位图来存储有关输入的信息;这将最大输入大小限制为64,因此我想创建一个整数被bitset或简单大整数替换的版本。我开始使用vector< bool>写一些东西,但环顾四周,我看到很多答案告诉我要避免矢量< bool>。
我需要的操作:
当它们被创建时,我知道最大位数,但起初我只需要1位;然后,在每一步,一组向左移动而另一组将有一个新的最高位:
{
a <<= 1;
a[0] = x;
b[++msb] = y;
if (a < b) b = a;
}
如果我创建了大小为1的位集,然后逐渐扩展它们,那么比较可能比我立即将长度设置为最大并且可能有数千个前导零更快?
我应该继续使用vector&lt; bool&gt;或者使用std :: bitset(不幸的是固定大小)或者使用无符号整数向量写一个简单的biginteger实现,只能执行上面提到的操作?
使用vector&lt; bool&gt;你可以用零长度初始化向量:
std::vector<bool> a(0), b(0);
然后执行上面提到的操作:
{
a.push_back(x);
b.insert(b.begin(), y);
if (a < b) b = a;
}
答案 0 :(得分:4)
我认为boost::dynamic_bitset
就是你所追求的目标。
以下是满足您要求的示例:
#include <iostream>
#include <boost/dynamic_bitset.hpp>
int main() {
boost::dynamic_bitset<> a(3, 2); // a = 010
a[0] = true; // a = 011
a.push_back(true); // a = 1011
boost::dynamic_bitset<> b = a; // b = 1011
a <<= 1; // a = 0110
bool aless = a < b; // true
unsigned long al = a.to_ulong(); // al = 6
std::cout << "a=" << a << ", al=" << a.to_ulong() << "\n"
<< "b=" << b << ", bl=" << b.to_ulong() << "\n"
<< "a<b=" << (a<b) << "\n";
}
一些注意事项:
dynamic_bitset<>(1, 1)
。遗憾的是,没有initializer_list
构造函数,所以你不能只做a = {true}
。也许最明显的事情是默认构造对象并在单独的一行上push_back(true)
。push_back
影响最重要的位,即左侧的值。那是因为“front”表示元素0,这是最不重要的位。a.push_back(false)
(你推的价值无关紧要,因为它会在一瞬间被扔掉)。a <<= 1
a[0] = x
如果您想设置新值。to_ulong()
仅在对象的元素足够少以适合您平台上的unsigned long
时才有效。请注意,它不是unsigned long long
,因此即使在64位系统上也可能是32位。any()
,all()
和count()
。答案 1 :(得分:0)
您描述的操作(将隐式解释省略为整数)实际上是由deque有效提供的操作。如果您可以容忍内存开销,可以使用std::deque<bool>
(std::list<bool>
也可以使用,但会有更高的开销。)
如果开销太大,可以从
开始struct Bits {
std::deque<unsigned> deq;
int ms_free,ls_free; // unused bits in the two end words
};
并编写方法以在两端推送位(对于右端,如果deq.push_back()
则为lsb_free==0
,否则将存储到 deq.back()
。比较将使用deq.size()
和ms_free+ls_free
来了解如何对齐两个序列。