This commit is contained in:
Gregory Burd 2024-04-09 17:10:22 -04:00
parent 92b6cc00db
commit 1ea0871506
2 changed files with 31 additions and 37 deletions

View file

@ -429,10 +429,9 @@ __sm_chunk_map_select(__sm_chunk_t *map, size_t n, ssize_t *pnew_n)
* Counts the set bits in the range [first, last] inclusive.
*/
static size_t
__sm_chunk_map_rank(__sm_chunk_t *map, size_t first, size_t last, size_t *after)
__sm_chunk_map_rank(__sm_chunk_t *map, size_t last, size_t *after)
{
size_t ret = 0;
(void)first; // TODO
register uint8_t *p = (uint8_t *)map->m_data;
for (size_t i = 0; i < sizeof(sm_bitvec_t); i++, p++) {
@ -480,24 +479,10 @@ __sm_chunk_map_rank(__sm_chunk_t *map, size_t first, size_t last, size_t *after)
*after = 0;
}
} else {
uint64_t mask_l, mask_r, mask;
if (*after > 0) {
if (*after > last) {
*after = *after - last;
/* This gives us 'last' number of ones on the right. */
mask_r = ((uint64_t)1 << last) - 1;
} else {
/* This gives us '*after' number of ones on the right. */
mask_r = (((uint64_t)1 << *after) - 1);
*after = 0;
}
/* Used to shift the mask_r block to the left 'last' times. */
mask_l = ((uint64_t)1 << (last + 1));
mask = mask_l - 1 - mask_r;
} else {
mask = UINT64_MAX >> (SM_BITS_PER_VECTOR - last - 1);
}
/* Create a mask for the range between *after and last. */
uint64_t mask;
/* Create a mask for the range between after and last inclusive [*after, last]. */
mask = ((uint64_t)1 << (last + 1)) - 1 - (((uint64_t)1 << *after) - 1);
*after -= (*after > last) ? last : *after;
uint64_t mw = w & mask;
ret += popcountll(mw);
return (ret);
@ -1207,7 +1192,7 @@ sparsemap_rank(sparsemap_t *map, size_t first, size_t last)
__sm_chunk_t chunk;
__sm_chunk_map_init(&chunk, p);
result += __sm_chunk_map_rank(&chunk, first - start, last - start, &after);
result += __sm_chunk_map_rank(&chunk, last - start, &after);
p += __sm_chunk_map_get_size(&chunk);
}
return (result);

View file

@ -550,16 +550,16 @@ test_api_rank(const MunitParameter params[], void *data)
/* rank() is also 0-based, for consistency (and confusion sake); consider the
range as [start, end] of [0, 9] counts the bits set in the first 10
positions (starting from the LSB) in the index. */
r1 = sparsemap_rank(map, 0, 9);
r2 = rank_uint64((uint64_t)-1, 0, 9);
r1 = rank_uint64((uint64_t)-1, 0, 9);
r2 = sparsemap_rank(map, 0, 9);
assert_true(r1 == r2);
assert_true(sparsemap_rank(map, 0, 9) == 10);
assert_true(sparsemap_rank(map, 1000, 1050) == 0);
for (int i = 0; i < 10; i++) {
for (int j = i; j < 10; j++) {
r1 = sparsemap_rank(map, i, j);
r2 = rank_uint64((uint64_t)-1, i, j);
r1 = rank_uint64((uint64_t)-1, i, j);
r2 = sparsemap_rank(map, i, j);
assert_true(r1 == r2);
}
}
@ -597,9 +597,18 @@ test_api_span(const MunitParameter params[], void *data)
for (int j = 1; j < amt / 10; j++) {
sparsemap_clear(map);
placed_at = create_sequential_set_in_empty_map(map, amt, j);
// whats_set(map, amt);
located_at = sparsemap_span(map, 0, j);
assert_true(located_at == placed_at);
}
}
for (int i = 1; i < amt; i++) {
for (int j = 1; j < amt / 10; j++) {
sparsemap_clear(map);
populate_map(map, 1024, 3 * 1024);
placed_at = create_sequential_set_in_empty_map(map, amt, j);
located_at = sparsemap_span(map, 0, j);
assert_true(located_at <= placed_at);
//TODO located_at = sparsemap_span(map, (placed_at < j ? 0 : placed_at / 2), i);
// assert_true(placed_at == located_at);
}