basic puzzle
This commit is contained in:
parent
4be954b9d0
commit
684ab1565f
|
@ -35,7 +35,7 @@ struct Args {
|
|||
|
||||
/// Create puzzle
|
||||
#[arg(long)]
|
||||
puzzle: bool,
|
||||
puzzle: Option<usize>,
|
||||
}
|
||||
|
||||
|
||||
|
@ -58,8 +58,8 @@ fn main() {
|
|||
return
|
||||
}
|
||||
|
||||
let result = if args.puzzle {
|
||||
solver.make_puzzle().map(|_| ())
|
||||
let result = if let Some(difficulty) = args.puzzle {
|
||||
solver.make_puzzle(difficulty).map(|_| ())
|
||||
} else {
|
||||
solver.solve(args.limit).map(|_| ())
|
||||
};
|
||||
|
|
|
@ -139,30 +139,35 @@ impl Solver {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn make_puzzle(&mut self) -> Result<(), WaveError> {
|
||||
pub fn make_puzzle(&mut self, difficulty: usize) -> Result<(), WaveError> {
|
||||
self.solve_display = false;
|
||||
println!("# generating full...");
|
||||
println!("\n# generating full...");
|
||||
let _ = self.solve(None)?;
|
||||
|
||||
println!("\n\n# erasing cells...");
|
||||
let mut rng = rand::thread_rng();
|
||||
|
||||
let erase_cell = loop {
|
||||
let pos = (rng.gen_range(1..=self.size), rng.gen_range(1..=self.size));
|
||||
if let Some(state) = self.grid[pos.0][pos.1].get_state() {
|
||||
self.grid[pos.0][pos.1].reset_state();
|
||||
break (pos, state);
|
||||
}
|
||||
};
|
||||
|
||||
let blocking_cell = cell::BlockingCell {
|
||||
state: erase_cell.1,
|
||||
position: erase_cell.0,
|
||||
};
|
||||
|
||||
self.propagate_backtrack(erase_cell.0, blocking_cell); // get min allowed state number
|
||||
// while min state number < 2 => loop
|
||||
let mut min_num_allowed = 1;
|
||||
|
||||
while min_num_allowed <= difficulty {
|
||||
let erase_cell = loop {
|
||||
let pos = (rng.gen_range(0..self.size), rng.gen_range(0..self.size));
|
||||
if let Some(state) = self.grid[pos.0][pos.1].get_state() {
|
||||
self.grid[pos.0][pos.1].reset_state();
|
||||
break (pos, state);
|
||||
}
|
||||
};
|
||||
let blocking_cell = cell::BlockingCell {
|
||||
state: erase_cell.1,
|
||||
position: erase_cell.0,
|
||||
};
|
||||
min_num_allowed = self.propagate_backtrack(erase_cell.0, blocking_cell);
|
||||
if min_num_allowed > difficulty {
|
||||
let _ = self.grid[erase_cell.0.0][erase_cell.0.1].collapse(&cell::CollapseOption::Set(erase_cell.1));
|
||||
//println!("put back ({},{}) to {}", erase_cell.0.0, erase_cell.0.1, erase_cell.1);
|
||||
//self.propagate_collapse(erase_cell.0, blocking_cell);
|
||||
}
|
||||
}
|
||||
|
||||
println!();
|
||||
self.display(ui::DisplayMode::Full);
|
||||
|
|
|
@ -74,7 +74,9 @@ impl Solver {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
pub fn propagate_backtrack(&mut self, cell_pos: (usize, usize), removed_cell: cell::BlockingCell) {
|
||||
pub fn propagate_backtrack(&mut self, cell_pos: (usize, usize), removed_cell: cell::BlockingCell) -> usize {
|
||||
let mut min_allowed_number = self.size;
|
||||
|
||||
for index in 0..self.size {
|
||||
if index != cell_pos.0 {
|
||||
self.grid[index][cell_pos.1].add_allowed(&removed_cell);
|
||||
|
@ -87,6 +89,12 @@ impl Solver {
|
|||
if square_row != cell_pos.0 || square_column != cell_pos.1 {
|
||||
self.grid[square_row][square_column].add_allowed(&removed_cell);
|
||||
}
|
||||
let num_allowed = self.grid[square_row][square_column].get_num_allowed();
|
||||
if num_allowed < min_allowed_number {
|
||||
min_allowed_number = num_allowed
|
||||
}
|
||||
}
|
||||
|
||||
min_allowed_number
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue