Я работаю над проектом, и я решил go с этой диаграммой классов:
Во время тестов все работало нормально поэтому я решил сделать это правильно и убедиться, что все типы были указаны просто, чтобы избежать проблем в будущем. Проблема в том, что для этого мне нужно импортировать больше классов, и я получаю циклический импорт.
В некоторых местах я читал, что эта проблема обычно из-за плохого дизайна. Я не думаю, что это так. В других местах я читал, что не должен проверять типы. Это вариант, но он мне не нравится. Я также читал о других способах решения этой проблемы, но ни один из них, кажется, не является реальным решением.
Я знаю, что Python не Java, но поскольку импорт, который создает мои проблемы, просто использовал для указания типа параметров методов Я думал, что, возможно, есть способ указать это внутри программы python, чтобы при круговом импорте не избежать выполнения программы.
Спасибо, если вам нужна какая-либо другая информация, просто спросите, и я отвечу как можно скорее.
РЕДАКТИРОВАТЬ:
Это вывод терминала:
[edoelas@leonardo server]$ env DEBUGPY_LAUNCHER_PORT=44765 /usr/bin/python /home/edoelas/.vscode/extensions/ms-python.python-2020.3.71113/pythonFiles/lib/python/debugpy/no_wheels/debugpy/launcher /home/edoelas/git/tfg/server/main.py
Traceback (most recent call last):
File "/home/edoelas/git/tfg/server/main.py", line 1, in <module>
from classes.actions.Move import Move
File "/home/edoelas/git/tfg/server/classes/actions/Move.py", line 2, in <module>
from classes.Entity import Entity
File "/home/edoelas/git/tfg/server/classes/Entity.py", line 3, in <module>
from classes.ActionType import ActionType
File "/home/edoelas/git/tfg/server/classes/ActionType.py", line 5, in <module>
from classes.Entity import Entity
ImportError: cannot import name 'Entity' from partially initialized module 'classes.Entity' (most likely due to a circular import) (/home/edoelas/git/tfg/server/classes/Entity.py)
И вот эти файлы:
Main.py
from classes.actions.Move import Move
from classes.Position import Position
from classes.Game import Game
from classes.Entity import Entity
from classes.Client import Client
from classes.Map import Map
if __name__ == "__main__":
map1 = Map()
client1 = Client("localhost",1000)
position1 = Position(0,0)
action1 = Move()
entity1 = Entity("test",100,1,[action1],client1,position1,map1)
id1 = 1
entity1.id = id1
ground_matrix = [
[0,0,0,0],
[0,0,0,0],
[0,0,0,0],
[0,0,0,0],
]
entity_matrix = [
[id1,0,0,0],
[0,0,0,0],
[0,0,0,0],
[0,0,0,0],
]
map1.load_map(ground_matrix,entity_matrix)
game = Game("ip", 1000, "asd")
game.add_entity(entity1)
print(map1.entity_matrix)
print(entity1.position)
position2 = Position(1,0)
entity1.loadAction(action1,position2)
entity1.executeAction()
action1.emiting_area
print(map1.entity_matrix)
print(entity1.position)
Move.py
from classes.Position import Position
from classes.Entity import Entity
from classes.ActionType import ActionType
from classes.Area import Area
class Move(ActionType):
def __init__(self):
self.emiting_area
@property
def emiting_area(self) -> Area:
return self.__emiting_area
@emiting_area.setter
def emiting_area(self, emiting_area: Area) -> None:
self.__emiting_area = emiting_area
def execute(self,emitter: Entity,target_position: Position) -> None:
emitter.position = target_position
Entity.py
# pyright: strict
from classes.ActionType import ActionType
from classes.Map import Map
from classes.Position import Position
from classes.Client import Client
from classes.Action import Action
from typing import List
class Entity:
"""
The entities are added from the Game object
"""
def __init__(self, name: str, max_health: int,team: int,
possible_actions: List[ActionType], client: Client,position: Position,map: Map):
self.__id: int
self.__name: str = name
self.max_health: int= max_health
self.team: int = team
self.health: int = max_health
self.possible_actions: List[ActionType] = possible_actions
self.__action_buffer: List[Action] = []
self.client: Client = client
self.__position: Position = position
#Map is here in order to update it each time an entity moves
self.map: Map = map
@property
def position(self) -> Position:
return self.__position
@position.setter
def position(self, new_position: Position):
self.__position = new_position
self.map.update_entity(self.id,self.__position,new_position)
@property
def id(self) -> int:
return self.__id
@id.setter
def id(self,id: int):
#Si la id ya ha sido asignada lanzar error
self.__id = id
def loadAction(self,actionType: ActionType,target_position: Position) -> None:
action = Action(actionType, self,target_position)
self.__action_buffer.append(action)
def executeAction(self) -> None:
action = self.__action_buffer.pop(0)
action.execute()
ActionType.py
# pyright: strict
from abc import abstractmethod
from classes.Position import Position
from classes.Entity import Entity
class ActionType:
def __init__(self):
raise NotImplementedError
@property
@abstractmethod
def emiting_area(self) -> None:
raise NotImplementedError
@property
@abstractmethod
def receiving_area(self) -> None:
raise NotImplementedError
@abstractmethod
def execute(self,emiter: Entity,target_position: Position) -> None:
raise NotImplementedError