New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Removing a counterproductive optimization. #375
Conversation
@richardstartin : can you have a look? This PR will undo one of your optimizations. I think it is counterproductive to check the cardinality first as it forces two traversal through the bitmap. |
Makes sense, actually I just ported this logic from CRoaring in the first place. Might be worth running the fuzz tests before removing it. |
@richardstartin I think you need to click on "approve" (as I formally asked you to approve this PR). @incaseoftrouble can you check whether this fixes your issue? I suspect that it will. |
@richardstartin The code in C does not have this optimization... bool roaring_bitmap_is_subset(const roaring_bitmap_t *ra1,
const roaring_bitmap_t *ra2) {
const int length1 = ra1->high_low_container.size,
length2 = ra2->high_low_container.size;
int pos1 = 0, pos2 = 0;
while (pos1 < length1 && pos2 < length2) {
const uint16_t s1 = ra_get_key_at_index(&ra1->high_low_container, pos1);
const uint16_t s2 = ra_get_key_at_index(&ra2->high_low_container, pos2);
if (s1 == s2) {
uint8_t container_type_1, container_type_2;
void *c1 = ra_get_container_at_index(&ra1->high_low_container, pos1,
&container_type_1);
void *c2 = ra_get_container_at_index(&ra2->high_low_container, pos2,
&container_type_2);
bool subset =
container_is_subset(c1, container_type_1, c2, container_type_2);
if (!subset) return false;
++pos1;
++pos2;
} else if (s1 < s2) { // s1 < s2
return false;
} else { // s1 > s2
pos2 = ra_advance_until(&ra2->high_low_container, s1, pos2);
}
}
if (pos1 == length1)
return true;
else
return false;
} |
Got around the bureaucratic check. |
Merging. Will release soon. |
@lemire you're right, but I definitely don't remember adding this as an optimisation, possibly for correctness or just absent-mindedness. I'll run the some of the fuzz tests on this to check. |
@lemire Thanks for pushing this so fast! 👍 |
@lemire this was added in |
@richardstartin Thank you. Note the benchmark that I added... this optimization definitively made things much, much slower (like hundreds of times) in some cases. So I have to thank @incaseoftrouble. |
Once again, it wasn’t an optimisation 👍 |
Ok. Fair enough. But it looked like one when I stared at the code. BTW it is not obvious why it would be bad. You have to sit down and think hard. |
In general whenever the bitmaps are passed over twice it costs (could also improve xorCardinality by calculating the cardinality containerwise rather than bitmap wise to avoid multiple bitmap passes) when the bitmaps are large... on this occasion it wasn’t an unprofiled optimisation obtained by a process of divination, but a hack. |
Also, this is a problem whenever you don’t have access to modify the source code... any boolean circuit which could be calculated in a single pass over the containers can end up passing over bitmaps several times, and it has a cost. |
Right. There might be clever techniques to get around this without forcing people to hack the internals. |
This is related to PR
#374
cc @incaseoftrouble