pub fn binary_search<T: PartialOrd>(array: &[T], element: &T) -> Result<usize, usize> {
let mut left_idx: usize = 0;
let mut right_idx: usize = array.len();
while left_idx < right_idx {
let mid_idx = (left_idx + right_idx) / 2;
if &array[mid_idx] < element {
left_idx = mid_idx + 1;
} else if &array[mid_idx] > element {
right_idx = mid_idx;
} else {
return Ok(mid_idx);
}
}
return Err(left_idx);
}
#[cfg(test)]
mod test {
use super::*;
macro_rules! test_cases {
($($name:ident: $test_case:expr,)*) => {
$(
#[test]
fn $name() {
let (arr, element, expected) = $test_case;
assert_eq!(binary_search(arr, element), expected);
}
)*
};
}
test_cases! {
empty: (&[],&0,Err(0)),
one_element: (&[1],&1,Ok(0)),
one_element_not_found: (&[1],&0,Err(0)),
string_one: (&["a","b"],&"a",Ok(0)),
string: (&["a","b","c","e","g"],&"c",Ok(2)),
string_now_found: (&["a","b","c","e","g"],&"d",Err(3)),
}
}