#[inline]
pub fn shrink_word(mut value: u32, is_failure: impl Fn(u32) -> bool) -> u32 {
if !is_failure(value) {
return value;
}
for candidate in [
0,
1,
2,
i32::MAX as u32,
i32::MIN as u32,
value.wrapping_sub(1),
] {
if candidate != value && is_failure(candidate) {
value = candidate;
}
}
loop {
let candidate = value / 2;
if candidate == value || !is_failure(candidate) {
break;
}
value = candidate;
}
value
}
#[inline]
pub fn shrink_words(mut values: Vec<u32>, is_failure: impl Fn(&[u32]) -> bool) -> Vec<u32> {
if !is_failure(&values) {
return values;
}
for index in 0..values.len() {
let original = values[index];
values[index] = shrink_word(original, |candidate| {
let mut trial = values.clone();
trial[index] = candidate;
is_failure(&trial)
});
}
values
}