fixed a_Star algorithm
This commit is contained in:
parent
37dc6d5595
commit
6a08195fe0
23
src/const.py
23
src/const.py
@ -1,8 +1,9 @@
|
|||||||
import os
|
import os
|
||||||
import pygame as pg
|
import pygame as pg
|
||||||
|
|
||||||
|
from ap_mine import APMine
|
||||||
from image import Image
|
from image import Image
|
||||||
|
from tile import Tile
|
||||||
|
|
||||||
main_path = os.path.dirname(os.getcwd())
|
main_path = os.path.dirname(os.getcwd())
|
||||||
|
|
||||||
@ -53,14 +54,14 @@ for name in [
|
|||||||
|
|
||||||
|
|
||||||
DEBUG_FIELD = [
|
DEBUG_FIELD = [
|
||||||
[1, 11, 1, 1, 1, 1, 1, 1, 1, 1],
|
[Tile(1, 1), Tile(11, 20), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1)],
|
||||||
[1, 1, 1, 1, 4, 1, 1, 1, 1, 1],
|
[Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(4, 1, APMine()), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1)],
|
||||||
[11, 1, 1, 1, 11, 4, 1, 1, 1, 1],
|
[Tile(11, 20), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(11, 20), Tile(4, 0, APMine()), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1)],
|
||||||
[4, 1, 1, 1, 11, 1, 1, 4, 1, 1],
|
[Tile(4, 0, APMine()), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(11, 20), Tile(1, 1),Tile(1, 1), Tile(4, 0, APMine()), Tile(1, 1),Tile(1, 1)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 11, 1, 1],
|
[Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(11, 20), Tile(1, 1), Tile(1, 1)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 11, 4, 1],
|
[Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(11, 20), Tile(4, 0, APMine()), Tile(1, 1)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 11, 1, 1],
|
[Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(1, 1), Tile(11, 20), Tile(1, 1), Tile(1, 1)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
|
[Tile(1, 1) for _ in range(10)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
|
[Tile(1, 1) for _ in range(10)],
|
||||||
[1, 1, 1, 1, 1, 1, 1, 1, 1, 1],
|
[Tile(1, 1) for _ in range(10)],
|
||||||
]
|
]
|
||||||
|
@ -8,10 +8,10 @@ from tilesFactory import TilesFactory
|
|||||||
def generate_field() -> List[List[Tile]]:
|
def generate_field() -> List[List[Tile]]:
|
||||||
tiles_factory = TilesFactory()
|
tiles_factory = TilesFactory()
|
||||||
tiles_list = tiles_factory.get_tiles_list()
|
tiles_list = tiles_factory.get_tiles_list()
|
||||||
return [choices(tiles_list, weights=[10, 10, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2], k=10) for _ in range(10)]
|
return [choices(tiles_list, weights=[10, 10, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4], k=10) for _ in range(10)]
|
||||||
|
|
||||||
|
|
||||||
class Environment:
|
class Environment:
|
||||||
def __init__(self, field: List[List[Tile]] = None):
|
def __init__(self, field: List[List[Tile]] = None):
|
||||||
self.field = field if field else generate_field()
|
self.field = generate_field()
|
||||||
self.mine_count = sum(sum(1 for tile in row if tile.mine) for row in self.field)
|
self.mine_count = sum(sum(1 for tile in row if tile.mine) for row in self.field)
|
||||||
|
14
src/main.py
14
src/main.py
@ -1,13 +1,11 @@
|
|||||||
from typing import Tuple
|
|
||||||
|
|
||||||
import pygame as pg
|
import pygame as pg
|
||||||
|
|
||||||
from agent import Agent
|
from agent import Agent
|
||||||
from game_ui import GameUi
|
from game_ui import GameUi
|
||||||
from const import ICON, IMAGES
|
from const import ICON, IMAGES
|
||||||
from environment import Environment
|
from environment import Environment
|
||||||
from search_algoritms.BFS import breadth_first_search
|
from search_algoritms.BFS import breadth_first_search, breadth_first_search_for_a_star
|
||||||
from src.search_algoritms.a_star import a_star, nearest_bomb
|
from src.search_algoritms.a_star import a_star
|
||||||
from tilesFactory import TilesFactory
|
from tilesFactory import TilesFactory
|
||||||
|
|
||||||
|
|
||||||
@ -64,11 +62,12 @@ def main():
|
|||||||
elif event.type == pg.KEYDOWN:
|
elif event.type == pg.KEYDOWN:
|
||||||
if event.key == pg.K_t:
|
if event.key == pg.K_t:
|
||||||
print('Starting to clear the sector')
|
print('Starting to clear the sector')
|
||||||
#while env.mine_count:
|
while env.mine_count:
|
||||||
print('-'*20)
|
print('-'*20)
|
||||||
#path, actions = breadth_first_search(env.field, agent.x, agent.y, agent.direction)
|
#path, actions = breadth_first_search(env.field, agent.x, agent.y, agent.direction)
|
||||||
#xd: Tuple[int,int] = Tuple[agent.x, agent.y]
|
path, actions = a_star (env.field, agent.x, agent.y, agent.direction,
|
||||||
path, actions = a_star(env.field, agent.x, agent.y, agent.direction, nearest_bomb((agent.x, agent.y), env.field))
|
breadth_first_search_for_a_star (env.field, agent.x, agent.y,
|
||||||
|
agent.direction))
|
||||||
if not path and not env.field[agent.y][agent.x].mine:
|
if not path and not env.field[agent.y][agent.x].mine:
|
||||||
print('Unable to find path, rocks are in the way')
|
print('Unable to find path, rocks are in the way')
|
||||||
break
|
break
|
||||||
@ -76,7 +75,6 @@ def main():
|
|||||||
print(f'Actions:{actions}')
|
print(f'Actions:{actions}')
|
||||||
for action in actions:
|
for action in actions:
|
||||||
pg.fastevent.post(pg.event.Event(pg.KEYDOWN, {'key': action}))
|
pg.fastevent.post(pg.event.Event(pg.KEYDOWN, {'key': action}))
|
||||||
|
|
||||||
pg.fastevent.post(pg.event.Event(pg.KEYDOWN, {'key': pg.K_SPACE}))
|
pg.fastevent.post(pg.event.Event(pg.KEYDOWN, {'key': pg.K_SPACE}))
|
||||||
handle_keys(env, agent, game_ui, factory)
|
handle_keys(env, agent, game_ui, factory)
|
||||||
print('Sector clear')
|
print('Sector clear')
|
||||||
|
@ -26,3 +26,25 @@ def breadth_first_search(field: List[List[Tile]], start_x: int, start_y: int, st
|
|||||||
node_queue.put(neighbour_node)
|
node_queue.put(neighbour_node)
|
||||||
|
|
||||||
return False, False
|
return False, False
|
||||||
|
|
||||||
|
|
||||||
|
def breadth_first_search_for_a_star(field: List[List[Tile]], start_x: int, start_y: int, start_direction: int):
|
||||||
|
explored = []
|
||||||
|
node_queue = queue.Queue()
|
||||||
|
node_queue.put(Node(start_x, start_y, start_direction))
|
||||||
|
|
||||||
|
while not node_queue.empty():
|
||||||
|
node = node_queue.get()
|
||||||
|
|
||||||
|
if field[node.y][node.x].mine:
|
||||||
|
return node.x, node.y
|
||||||
|
|
||||||
|
explored.append(node)
|
||||||
|
for x, y, direction, action in successor(field, node.x, node.y, node.direction):
|
||||||
|
neighbour_node = Node(x, y, direction, node, action)
|
||||||
|
node_queue_list = node_queue.queue
|
||||||
|
if neighbour_node in explored or neighbour_node in node_queue_list:
|
||||||
|
continue
|
||||||
|
node_queue.put(neighbour_node)
|
||||||
|
|
||||||
|
return False, False
|
@ -1,11 +1,10 @@
|
|||||||
from operator import itemgetter
|
|
||||||
from typing import List, Tuple
|
from typing import List, Tuple
|
||||||
|
|
||||||
from ap_mine import APMine
|
from ap_mine import APMine
|
||||||
from at_mine import ATMine
|
from at_mine import ATMine
|
||||||
from src.node import Node
|
from src.node import Node
|
||||||
from src.tile import Tile
|
from src.tile import Tile
|
||||||
from .helpers import successor, get_path_actions, calculate_priority
|
from .helpers import successor, get_path_actions_a_star, calculate_priority
|
||||||
|
|
||||||
|
|
||||||
def a_star(field: List[List[Tile]], start_x: int, start_y: int, start_direction: int, goal: Tuple[int, int]):
|
def a_star(field: List[List[Tile]], start_x: int, start_y: int, start_direction: int, goal: Tuple[int, int]):
|
||||||
@ -17,7 +16,7 @@ def a_star(field: List[List[Tile]], start_x: int, start_y: int, start_direction:
|
|||||||
# przy get wyciąga element z najniższą wartością priorytetu
|
# przy get wyciąga element z najniższą wartością priorytetu
|
||||||
|
|
||||||
if (node.x, node.y) == goal:
|
if (node.x, node.y) == goal:
|
||||||
return get_path_actions(node)
|
return get_path_actions_a_star(node, field)
|
||||||
|
|
||||||
explored.append(node)
|
explored.append(node)
|
||||||
for x, y, direction, action in successor(field, node.x, node.y, node.direction):
|
for x, y, direction, action in successor(field, node.x, node.y, node.direction):
|
||||||
@ -48,4 +47,4 @@ def nearest_bomb(a: Tuple[int, int], field: List[List[Tile]]):
|
|||||||
min = distance
|
min = distance
|
||||||
min_x = x
|
min_x = x
|
||||||
min_y = y
|
min_y = y
|
||||||
return (min_x, min_y)
|
return min_x, min_y
|
||||||
|
@ -28,7 +28,7 @@ def successor(field: List[List[Tile]], x: int, y: int, direction: int):
|
|||||||
return neighbours
|
return neighbours
|
||||||
|
|
||||||
|
|
||||||
def get_path_actions(node: Node):
|
def get_path_actions(node: Node, field: List[List[Tile]]):
|
||||||
path = []
|
path = []
|
||||||
actions = []
|
actions = []
|
||||||
while node.parent:
|
while node.parent:
|
||||||
@ -37,6 +37,18 @@ def get_path_actions(node: Node):
|
|||||||
node = node.parent
|
node = node.parent
|
||||||
return path[::-1], actions[::-1]
|
return path[::-1], actions[::-1]
|
||||||
|
|
||||||
|
def get_path_actions_a_star(node: Node, field: List[List[Tile]]):
|
||||||
|
path = []
|
||||||
|
actions = []
|
||||||
|
while node.parent:
|
||||||
|
path.append((node.x, node.y))
|
||||||
|
print(field[node.y][node.x], field[node.y][node.x].weight, node.x, node.y, field[node.y][node.x].mine)
|
||||||
|
if field[node.y][node.x].mine:
|
||||||
|
actions.append(32)
|
||||||
|
actions.append(node.action)
|
||||||
|
node = node.parent
|
||||||
|
return path[::-1], actions[::-1]
|
||||||
|
|
||||||
|
|
||||||
def cost(field: List[List[Tile]], node):
|
def cost(field: List[List[Tile]], node):
|
||||||
return 1 if (node.parent.x, node.parent.y) == (node.x, node.y) else field[node.y][node.x].weight
|
return 1 if (node.parent.x, node.parent.y) == (node.x, node.y) else field[node.y][node.x].weight
|
||||||
|
@ -10,9 +10,9 @@ class TilesFactory:
|
|||||||
img = IMAGES[number]
|
img = IMAGES[number]
|
||||||
if img.mine_type:
|
if img.mine_type:
|
||||||
module = import_module(f'{img.mine_type.lower()}_mine')
|
module = import_module(f'{img.mine_type.lower()}_mine')
|
||||||
return Tile(number, 1, getattr(module, f'{img.mine_type}Mine')())
|
return Tile(number, 0, getattr(module, f'{img.mine_type}Mine')())
|
||||||
else:
|
else:
|
||||||
return Tile(number, 1) if 'grass' in img.name else Tile(number, 20)
|
return Tile(number, 5) if 'grass' in img.name else Tile(number, 30)
|
||||||
|
|
||||||
def get_tiles_list(self) -> List[Tile]:
|
def get_tiles_list(self) -> List[Tile]:
|
||||||
return [self.create_tile(i) for i in range(13)]
|
return [self.create_tile(i) for i in range(13)]
|
||||||
|
Loading…
Reference in New Issue
Block a user