}
+bin64_t bins::find_filtered
+ (bins& filter, const bin64_t range, const uint8_t layer, fill_t seek)
+{
+ iterator i(this,range,true), j(&filter,range,true);
+ fill_t stop = seek==EMPTY ? FILLED : EMPTY;
+ while (true) {
+ while ( i.bin().layer()>layer && (i.deep() || *i!=stop || j.deep() || *j!=EMPTY) )
+ i.left(), j.left(); // TODO may optimize a lot here
+ if (i.bin().layer()==layer && !i.deep() && *i==seek && *j==EMPTY)
+ return i.bin();
+ while (i.bin().is_right() && i.bin()!=range)
+ i.parent(), j.parent();
+ if (i.bin()==range)
+ break;
+ i.parent(), j.parent();
+ i.right(), j.right();
+ }
+ return bin64_t::NONE;
+}
+
+void bins::set_range (bins& origin, bin64_t range) { // FIXME unite with remove(); do bitwise()
+ iterator zis(this,range,true), zat(&origin,range,true);
+ while (zis.pos.within(range)) {
+ while (zis.deep() || zat.deep()) {
+ zis.left(); zat.left();
+ }
+
+ *zis = *zat;
+
+ while (zis.pos.is_right()) {
+ zis.parent(); zat.parent();
+ }
+ zis.sibling(); zat.sibling();
+ }
+}
+
binheap::binheap() {
size_ = 32;
heap_ = (bin64_t*) malloc(size_*sizeof(bin64_t));
void set (bin64_t bin, fill_t val=FILLED);
+ void set_range (bins& origin, bin64_t range);
+
bin64_t find (const bin64_t range, const uint8_t layer, fill_t seek=EMPTY) ;
+ bin64_t find_filtered
+ (bins& filter, const bin64_t range, const uint8_t layer, fill_t seek=EMPTY) ;
+
void remove (bins& b);
void dump(const char* note);
bool empty () const { return !deep(0) && !halves[0]; }
+ static bool is_mixed (uint16_t val) { return val!=EMPTY && val!=FILLED; }
+
private:
/** Every 16th uint32 is a flag field denoting whether
}
+TEST(BinsTest,FindFiltered) {
+
+ bins data, filter;
+ data.set(bin64_t(2,0));
+ data.set(bin64_t(2,2));
+ data.set(bin64_t(1,7));
+ filter.set(bin64_t(2,1));
+ filter.set(bin64_t(1,4));
+ filter.set(bin64_t(0,13));
+
+ bin64_t x = data.find_filtered(filter,bin64_t(4,0),0);
+ EXPECT_EQ(bin64_t(0,12),x);
+
+}
+
+TEST(BinsTest,SetRange) {
+ bins data, add;
+ data.set(bin64_t(2,0));
+ data.set(bin64_t(2,2));
+ data.set(bin64_t(1,7));
+ add.set(bin64_t(2,1));
+ add.set(bin64_t(1,4));
+ add.set(bin64_t(0,13));
+ add.set(bin64_t(5,118));
+ data.set_range(add, bin64_t(3,0));
+ EXPECT_TRUE(bins::is_mixed(data.get(bin64_t(3,0))));
+ EXPECT_EQ(bins::EMPTY,data.get(bin64_t(2,0)));
+ EXPECT_EQ(bins::FILLED,data.get(bin64_t(2,1)));
+ EXPECT_EQ(bins::EMPTY,data.get(bin64_t(1,6)));
+ EXPECT_EQ(bins::FILLED,data.get(bin64_t(1,7)));
+}
+
TEST(BinheapTest,Eat) {
binheap b;