use crate::board::Board; use crate::strategy::{NakedSingle, Strategy, StrategyFn}; use crate::validator; fn try_strategies(strategies: &[StrategyFn], sudoku_board: &Board) -> Option> { for strategy in strategies { if let Some(strat) = strategy(&sudoku_board) { return Some(strat); } } None } pub fn solve_board(mut sudoku_board: Board) -> Result { if let validator::BoardState::Broken(ind) = validator::validate_board(&sudoku_board) { println!("{}", sudoku_board.to_url()); panic!( "Error invalid number at row {} col {}", (ind / 9) + 1, (ind % 9) + 1 ); } let strategies: [StrategyFn; 1] = [NakedSingle::find_instance]; while let Some(ns) = try_strategies(&strategies, &sudoku_board) { sudoku_board = ns.apply(sudoku_board); if let validator::BoardState::Broken(ind) = validator::validate_board(&sudoku_board) { println!("{}", sudoku_board.to_url()); panic!( "Error invalid number at row {} col {}", (ind / 9) + 1, (ind % 9) + 1 ); } } match validator::validate_board(&sudoku_board) { validator::BoardState::Finished => Ok(sudoku_board), validator::BoardState::InProgress => Err(sudoku_board), _ => unreachable!(), } }