Spooky / quantum /utils /validation.py
JavideuS's picture
Deploy 888d5f7
e516f1f verified
Raw
History Blame Contribute Delete
3.09 kB
"""
This module provides common validation functions used across QUBO builders,
solvers, and benchmarking tools.
"""
from typing import Tuple, Optional
def is_valid_move(
problem,
from_pos: Tuple[int, int],
to_pos: Tuple[int, int],
goal: Optional[Tuple[int, int]] = None
) -> bool:
"""
Check if a move from one position to another is valid.
Supports both grid and graph problem formats. Validates that positions
are adjacent according to the problem's adjacency structure.
Args:
problem: Problem instance (grid or graph)
from_pos: Starting position (i, j) coordinates
to_pos: Destination position (i, j) coordinates
goal: Optional goal position for goal-lock checking
Returns:
True if the move is valid (adjacent or same position), False otherwise
Examples:
>>> is_valid_move(problem, (0, 0), (0, 1)) # Adjacent cells
True
>>> is_valid_move(problem, (0, 0), (0, 0)) # Staying in place
True
>>> is_valid_move(problem, (0, 0), (5, 5)) # Non-adjacent
False
>>> is_valid_move(problem, (2, 3), (2, 3), goal=(2, 3)) # At goal
True
"""
# Same position is always valid (waiting/staying in place)
if from_pos == to_pos:
return True
# Allow staying at goal position
if goal is not None and from_pos == goal and to_pos == goal:
return True
problem_type = problem.get_format_type()
if problem_type == "grid":
# Check grid adjacency using adjacency dictionary
return to_pos in problem.grid.adjacency.get(from_pos, [])
else: # graph or both
# Check graph adjacency
from_node = problem.graph.get_node_from_position(from_pos)
to_node = problem.graph.get_node_from_position(to_pos)
if from_node is None or to_node is None:
return False
# Adjacency list stores (neighbor_node, weight) tuples
neighbors = [n for n, _ in problem.graph.adjacency.get(from_node, [])]
return to_node in neighbors
def get_position_representation(problem, position: Tuple[int, int]):
"""
Get the position representation appropriate for the problem type.
For grid problems, returns the position coordinates as-is.
For graph problems, returns the node ID corresponding to the position.
Args:
problem: Problem instance (grid or graph)
position: Position tuple (i, j)
Returns:
For grid: position tuple (i, j)
For graph: node ID (int)
Examples:
>>> get_position_representation(grid_problem, (2, 3))
(2, 3)
>>> get_position_representation(graph_problem, (2, 3))
15 # Node ID at position (2, 3)
"""
problem_type = problem.get_format_type()
if problem_type == "grid":
# Grid uses coordinates directly
return position
else: # graph or both
# Graph uses node IDs
return problem.graph.get_node_from_position(position)