document code

This commit is contained in:
2025-09-24 16:14:15 +02:00
parent 4451ef60e1
commit 7de3bfc6cd
2 changed files with 33 additions and 8 deletions

View File

@@ -58,9 +58,16 @@ class CSP:
"""
def revise(csp, xi, xj) -> bool:
"""Reduce the domain of xi if possible
Returns
-------
bool
Whether or not there was a domain reduction
"""
revised = False
for x in set(csp.domains[xi]):
if not any(
if not any( # translation of algorithm's forall expression.
[
(x, y) in csp.binary_constraints[(xi, xj)]
for y in csp.domains[xj]
@@ -97,39 +104,57 @@ class CSP:
A solution if any exists, otherwise None
"""
def backtrack(csp, assignment: dict[str, Any]) -> dict | None:
def backtrack(csp, assignment: dict[str, Any]) -> dict[str, Any] | None:
"""The recursive engine of backtracking_search.
Returns
-------
dict[str, Any]
The solution to bubble up
None
If current branch has no solution
"""
# this is read from stdout in sudoku.py. important to 2c).
# yes, it couldv'e been done differently, but this is
# quick and unintrusive.
print("i have been called")
if len(assignment) == len(csp.variables):
if len(assignment) == len(csp.variables): # completion condition
return assignment # base-case
var = select_unassigned_variable(csp, assignment)
for value in order_domain_values(csp, var, assignment):
if not consistent(csp, var, value, assignment):
continue
continue # do nothing (skip iteration)
assignment[var] = value
if result := backtrack(csp, assignment):
return result
return result # return if not failure
assignment.pop(var)
print("i have failed")
return None # failure
def consistent(csp, var, value, assignment) -> bool:
"""Helper function to determine if an arc is consistent"""
for v in assignment:
if (var, v) in csp.binary_constraints.keys():
if (value, assignment[v]) not in csp.binary_constraints[(var, v)]:
return False
if (v, var) in csp.binary_constraints.keys():
if (v, var) in csp.binary_constraints.keys(): # bi-birectional
if (value, assignment[v]) not in csp.binary_constraints[(v, var)]:
return False
return True
def select_unassigned_variable(csp, assignment) -> str:
"""Helper function to find a variable that is yet to be assigned."""
for v in csp.variables:
if v not in assignment.keys():
return v
return "this shouldn't happen"
# choose least constrained value
def order_domain_values(csp, var, assignment) -> list[Any]:
"""Helper function to order the domain values.
Orders on the least constrained value
"""
# calculate a sorting key by counting constraints
def compare(value) -> int:
s = 0
for neighbor in [
@@ -145,7 +170,7 @@ class CSP:
return sorted(list(csp.domains[var]), key=compare)
return backtrack(self, {})
return backtrack(self, {}) # start with no assignments
def alldiff(variables: list[str]) -> list[tuple[str, str]]:

Binary file not shown.