mirror of
https://github.com/wesnoth/wesnoth
synced 2025-05-14 12:35:47 +00:00
Add count_ones
function
Add the following function in `src/util.hpp`: template<typename N> inline unsigned int count_ones(N n); This function returns the quantity of `1` bits in `n` — i.e., `n`’s population count.
This commit is contained in:
parent
2313201837
commit
23fddb0e93
@ -89,6 +89,21 @@ BOOST_AUTO_TEST_CASE( test_bit_width )
|
||||
BOOST_CHECK( bit_width((boost::uint64_t) 0) == 64 );
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE( test_count_ones )
|
||||
{
|
||||
BOOST_CHECK( count_ones(0) == 0 );
|
||||
BOOST_CHECK( count_ones(1) == 1 );
|
||||
BOOST_CHECK( count_ones(2) == 1 );
|
||||
BOOST_CHECK( count_ones(3) == 2 );
|
||||
BOOST_CHECK( count_ones(4) == 1 );
|
||||
BOOST_CHECK( count_ones(5) == 2 );
|
||||
BOOST_CHECK( count_ones(6) == 2 );
|
||||
BOOST_CHECK( count_ones(7) == 3 );
|
||||
BOOST_CHECK( count_ones(8) == 1 );
|
||||
BOOST_CHECK( count_ones(9) == 2 );
|
||||
BOOST_CHECK( count_ones(12345) == 6 );
|
||||
}
|
||||
|
||||
/* vim: set ts=4 sw=4: */
|
||||
|
||||
BOOST_AUTO_TEST_SUITE_END()
|
||||
|
27
src/util.hpp
27
src/util.hpp
@ -237,6 +237,33 @@ inline std::size_t bit_width(const T& x) {
|
||||
return sizeof(x) * std::numeric_limits<unsigned char>::digits;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the quantity of `1` bits in `n` — i.e., `n`’s population count.
|
||||
*
|
||||
* Algorithm adapted from:
|
||||
* <https://graphics.stanford.edu/~seander/bithacks.html#CountBitsSetKernighan>
|
||||
*
|
||||
* This algorithm was chosen for relative simplicity, not for speed.
|
||||
*
|
||||
* @tparam N The type of `n`. This should be a fundamental integer type no
|
||||
* greater than `UINT_MAX` bits in width; if it is not, the return value is
|
||||
* undefined.
|
||||
*
|
||||
* @param n An integer upon which to operate.
|
||||
*
|
||||
* @returns the quantity of `1` bits in `n`, if `N` is a fundamental integer
|
||||
* type.
|
||||
*/
|
||||
template<typename N>
|
||||
inline unsigned int count_ones(N n) {
|
||||
unsigned int r = 0;
|
||||
while (n) {
|
||||
n &= n-1;
|
||||
++r;
|
||||
}
|
||||
return r;
|
||||
}
|
||||
|
||||
#ifdef __GNUC__
|
||||
#define LIKELY(a) __builtin_expect((a),1) // Tells GCC to optimize code so that if is likely to happen
|
||||
#define UNLIKELY(a) __builtin_expect((a),0) // Tells GCC to optimize code so that if is unlikely to happen
|
||||
|
Loading…
x
Reference in New Issue
Block a user