Reputation: 608
I'm using a Sha256 hashing function that returns [u8; 32] because the 256 bit long hash is too big to be represented in Rust's native types.
That's all fine but I need to generate a binary number from the hash and check how many leading zeros are in the binary number.
Is there any good way to do this?
As of now, I tried to convert each separate u8 to its binary form and concatenate them together, but that doesn't generate the right number.
pub fn to_bits(arr: &[u8; 32]) -> String {
let mut final_str = String::new();
for i in arr {
final_str.push_str(&format!("{:b}", i));
}
final_str
}
Upvotes: 0
Views: 1345
Reputation: 76509
You can actually do this without needing to convert it into another form. Each byte can be inspected for its leading zero bits with u8::leading_zeros
, so you could write something like this (tests included):
pub fn leading_bits(arr: &[u8; 32]) -> u32 {
let mut count = 0;
for x in arr {
let bits = x.leading_zeros();
count += bits;
if bits != 8 {
break;
}
}
count
}
#[cfg(test)]
mod tests {
use super::leading_bits;
#[test]
fn test_leading_bits() {
assert_eq!(leading_bits(&[0u8; 32]), 256);
assert_eq!(leading_bits(&[1u8; 32]), 7);
let mut buf = [0u8; 32];
buf[1] = 0x80;
assert_eq!(leading_bits(&buf), 8);
buf[1] = 0x00;
buf[2] = 0x0f;
assert_eq!(leading_bits(&buf), 20);
}
}
We look at each byte in turn. If a byte has less than 8 leading zeros in it, then we've seen at least one 1, so break out of the loop.
Upvotes: 5