Skip to content
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

Add some missing roaring64 functions #628

Merged
merged 2 commits into from
May 23, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions include/roaring/roaring64.h
Original file line number Diff line number Diff line change
Expand Up @@ -202,6 +202,11 @@ void roaring64_bitmap_remove_range(roaring64_bitmap_t *r, uint64_t min,
void roaring64_bitmap_remove_range_closed(roaring64_bitmap_t *r, uint64_t min,
uint64_t max);

/**
* Empties the bitmap.
*/
void roaring64_bitmap_clear(roaring64_bitmap_t *r);

/**
* Returns true if the provided value is present.
*/
Expand Down Expand Up @@ -272,6 +277,12 @@ uint64_t roaring64_bitmap_get_cardinality(const roaring64_bitmap_t *r);
uint64_t roaring64_bitmap_range_cardinality(const roaring64_bitmap_t *r,
uint64_t min, uint64_t max);

/**
* Returns the number of elements in the range [min, max]
*/
uint64_t roaring64_bitmap_range_closed_cardinality(const roaring64_bitmap_t *r,
uint64_t min, uint64_t max);

/**
* Returns true if the bitmap is empty (cardinality is zero).
*/
Expand Down
16 changes: 15 additions & 1 deletion src/roaring64.c
Original file line number Diff line number Diff line change
Expand Up @@ -707,6 +707,10 @@ void roaring64_bitmap_remove_range_closed(roaring64_bitmap_t *r, uint64_t min,
remove_range_closed_at(art, max_high48, 0, max_low16);
}

void roaring64_bitmap_clear(roaring64_bitmap_t *r) {
roaring64_bitmap_remove_range_closed(r, 0, UINT64_MAX);
}

uint64_t roaring64_bitmap_get_cardinality(const roaring64_bitmap_t *r) {
art_iterator_t it = art_init_iterator(&r->art, /*first=*/true);
uint64_t cardinality = 0;
Expand All @@ -724,7 +728,17 @@ uint64_t roaring64_bitmap_range_cardinality(const roaring64_bitmap_t *r,
if (min >= max) {
return 0;
}
max--; // A closed range is easier to work with.
// Convert to a closed range
// No underflow here: passing the above condition implies min < max, so
// there is a number less than max
return roaring64_bitmap_range_closed_cardinality(r, min, max - 1);
}

uint64_t roaring64_bitmap_range_closed_cardinality(const roaring64_bitmap_t *r,
uint64_t min, uint64_t max) {
if (min > max) {
return 0;
}

uint64_t cardinality = 0;
uint8_t min_high48[ART_KEY_BYTES];
Expand Down
23 changes: 23 additions & 0 deletions tests/roaring64_unit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -727,6 +727,29 @@ DEFINE_TEST(test_range_cardinality) {
// range is exclusive, so UINT64_MAX is not included
assert_int_equal(
roaring64_bitmap_range_cardinality(r, start, UINT64_MAX), 4);
// With an inclusive range, UINT64_MAX _is_ included
assert_int_equal(
roaring64_bitmap_range_closed_cardinality(r, start, UINT64_MAX), 5);

roaring64_bitmap_free(r);
}
{
// Empty ranges always have zero cardinality
roaring64_bitmap_t* r =
roaring64_bitmap_from(0, 1, 2, 3, 4, 5, UINT64_MAX);

assert_int_equal(roaring64_bitmap_range_cardinality(r, 1, 1), 0);
assert_int_equal(roaring64_bitmap_range_cardinality(r, 1, 0), 0);
assert_int_equal(roaring64_bitmap_range_cardinality(r, UINT64_MAX, 0),
0);
assert_int_equal(
roaring64_bitmap_range_cardinality(r, UINT64_MAX, UINT64_MAX), 0);
assert_int_equal(roaring64_bitmap_range_closed_cardinality(r, 1, 0), 0);
assert_int_equal(
roaring64_bitmap_range_closed_cardinality(r, UINT64_MAX, 0), 0);
assert_int_equal(roaring64_bitmap_range_closed_cardinality(
r, UINT64_MAX, UINT64_MAX - 1),
0);

roaring64_bitmap_free(r);
}
Expand Down
Loading