public PuzzlePathfinder <MoveT, StateT> RecalculateGrah(IPuzzleProcessor <MoveT, StateT> processor, StateT initialState, MoveT[] possibleMoves) { _statesToGraphMap = new Dictionary <StateT, Node>(); _graph = new List <Node>(); _winStates = new HashSet <Node>(); GenerateNodes(processor, initialState, possibleMoves, out List <List <StateT> > neighbourMap, out List <List <MoveT> > neighbourMovesMap); FindNodeNeighbours(neighbourMap, neighbourMovesMap); return(this); }
/// <summary> /// Creates nodes from posibble states /// </summary> /// <param name="processor">Puzzle processor</param> /// <param name="initialState">Initial position to test all possible puzzle states</param> /// <param name="possibleMoves">List of moves that can be performed</param> /// <param name="neighbourMap">Map that corresponds to all states that are neighbour to given node, is same order as _graph</param> /// <param name="neighbourMovesMap">Map that correcponds to all moves needed to get to neighbour states, same sizes as neighbourMap</param> /// <returns>List of neighbouring states for each state</returns> private void GenerateNodes(IPuzzleProcessor <MoveT, StateT> processor, StateT initialState, MoveT[] possibleMoves, out List <List <StateT> > neighbourMap, out List <List <MoveT> > neighbourMovesMap) { var statesToCheck = new Queue <StateT>(); var closedSet = new HashSet <StateT>(); neighbourMap = new List <List <StateT> >(); neighbourMovesMap = new List <List <MoveT> >(); statesToCheck.Enqueue(initialState); // Looking through every possible state while (statesToCheck.Count > 0) { var state = statesToCheck.Dequeue(); var node = new Node(state); if (processor.StateIsWinning(state)) { _winStates.Add(node); } _graph.Add(node); _statesToGraphMap.Add(state, node); closedSet.Add(state); // Iterating through posibble moves var neighbouringStates = new List <StateT>(); var neighbourMoves = new List <MoveT>(); foreach (var move in possibleMoves) { var newState = processor.Process(state, move); // State is not the same as original one and therefore this move changes state if (!state.Equals(newState) && !neighbouringStates.Contains(newState)) { // State was not tested and is not in the queue if (!closedSet.Contains(newState) && !statesToCheck.Contains(newState)) { statesToCheck.Enqueue(newState); } neighbouringStates.Add(newState); neighbourMoves.Add(move); } } neighbourMap.Add(neighbouringStates); neighbourMovesMap.Add(neighbourMoves); } }
public void Setup() { _processor = new FakePuzzleProcessor(); _pathfinder = new PuzzlePathfinder <int, char>().RecalculateGrah(_processor, 'A', new int[] { 1, 2, 3, 4 }); }