Make solver duplicate Wordle's behavior when a letter appears more times in the guess than in the answer
XDFAFLG4YP6F4QKKW3HOROK6I4MQTSB3OD2OQUFISA32P4IW6G2QC
if matches_byte_at_index(guess, ans, idx) {
let guess_char = byte_at_idx(guess, idx);
let ans_char = byte_at_idx(ans, idx);
let remaining = unsafe { counts.get_unchecked_mut((guess_char - b'a') as usize) };
if guess_char == ans_char {
*remaining -= 1;
} else if has_byte_at_index(guess, ans, idx) {
}
}
// assign yellows
for (idx, color) in response.iter_mut().enumerate() {
let guess_char = byte_at_idx(guess, idx);
let remaining = unsafe { counts.get_unchecked_mut((guess_char - b'a') as usize) };
if *remaining != 0 {
*remaining -= 1;
}
}
#[inline]
/// returns whether the `idx` letter in the word represented by `a` and `b` matches
fn matches_byte_at_index(a: u64, b: u64, idx: usize) -> bool {
// shift is opposite of index because of endianness
let shift = 4 - idx;
(a >> (shift * 8)) & 0xff == (b >> (shift * 8)) & 0xff
}
#[inline]
/// Finds whether `haystack` contains the letter at `idx` in the word represented by `needle`
fn has_byte_at_index(needle: u64, haystack: u64, idx: usize) -> bool {
// shift is opposite of index because of endianness
let shift = 4 - idx;
let byte = (needle >> (shift * 8)) & 0xff;
for cand_shift in 0..5 {
if (haystack >> (cand_shift * 8)) & 0xff == byte {
return true;
}
// it would be nice to just have this be compute_response(guess, candidate) == response
// but the short circuiting in this implementation saves considerable time
let mut counts = [0u8; 26];
for idx in 0..5 {
let count_idx = byte_at_idx(candidate, idx) - b'a';
unsafe { *counts.get_unchecked_mut(count_idx as usize) += 1 };
}
// mark greens
_ => continue,
}
}
// mark yellows
for (idx, color) in response.iter().copied().enumerate() {
let guess_char = byte_at_idx(guess, idx);
let cand_char = byte_at_idx(candidate, idx);
let remaining = unsafe { counts.get_unchecked_mut((guess_char - b'a') as usize) };
match color {
Color::Green => continue,
fn regression_test_compute_response() {
use Color::*;
assert_eq!(
compute_response(word_to_u64(b"worry"), word_to_u64(b"purge")),
[Black, Black, Green, Black, Black]
);
assert_eq!(
compute_response(word_to_u64(b"roate"), word_to_u64(b"purge")),
[Yellow, Black, Black, Black, Green]
);
assert_eq!(
compute_response(word_to_u64(b"roate"), word_to_u64(b"sling")),
[Black, Black, Black, Black, Black]
);
}
#[test]