Домашни > Хелоуин в Припят > Решения > Решението на Десислава Белчева

Резултати
10 точки от тестове
0 точки от учител

10 точки общо

12 успешни теста
0 неуспешни теста
Код
Скрий всички коментари

  1class Candy:
  2    def __init__(self, mass, uranium):
  3        self._mass = mass
  4        self._uranium = uranium
  5
  6    def get_uranium_quantity(self):
  7        return self._mass * self._uranium
  8
  9    def get_mass(self):
 10        return self._mass
 11
 12
 13class Person:
 14    def __init__(self, position):
 15        self._position = position
 16
 17    def get_position(self):
 18        return self._position
 19
 20    def set_position(self, new_position):
 21        self._position = new_position
 22
 23
 24class Kid(Person):
 25    def __init__(self, position, initiative):
 26        super().__init__(position)
 27        self._initiative = initiative
 28        self._basket_with_candies = []
 29
 30    def get_initiative(self):
 31        return self._initiative
 32
 33    def add_candy(self, candy):
 34        self._basket_with_candies.append(candy)
 35
 36    def is_critical(self):
 37        total_uranium = sum(candy.get_uranium_quantity()
 38                            for candy in self._basket_with_candies)
 39        return total_uranium > 20
 40
 41
 42class Host(Person):
 43    def __init__(self, position, candies):
 44        super().__init__(position)
 45        self._candies = [Candy(mass, uranium) for mass, uranium in candies]
 46
 47    def remove_candy(self, selection_function):
 48        if not self._candies:
 49            return None
 50        selected_candy = selection_function(self._candies)
 51        self._candies.remove(selected_candy)
 52        return selected_candy
 53
 54
 55class FluxCapacitor:
 56    def __init__(self, participants):
 57        self._kids = [p for p in participants if isinstance(p, Kid)]
 58        self._hosts = [p for p in participants if isinstance(p, Host)]
 59        self._victims = set()
 60        self._visited_hosts = {kid: set() for kid in self._kids}
 61
 62    @staticmethod
 63    def distance(pos1, pos2):
 64        return ((pos1[0] - pos2[0]) ** 2 + (pos1[1] - pos2[1]) ** 2) ** 0.5
 65    
 66    def closer_host(self, pos1, pos2):
 67        if pos1[0] == pos2[0]:
 68            return pos1[1] < pos2[1]
 69        return pos1[0] < pos2[0]
 70    
 71    def closest_host(self, kid):
 72        closest_host = None
 73        min_distance = float('inf')
 74        kid_position = kid.get_position()
 75        for host in self._hosts:
 76            if host not in self._visited_hosts[kid]: 
 77                host_position = host.get_position()
 78                distance = self.distance(kid_position, host_position)
 79                if distance < min_distance:
 80                    min_distance = distance
 81                    closest_host = host
 82                elif distance == min_distance:
 83                    if self.closer_host(host_position, closest_host.get_position()):
 84                        closest_host = host
 85        return closest_host, min_distance
 86
 87    def get_victim(self):
 88        while True:
 89            for kid in sorted(self._kids, key=lambda x: x.get_initiative(), reverse=True):
 90                closest_host, _ = self.closest_host(kid)
 91                if closest_host and closest_host not in self._visited_hosts[kid]:
 92                    kid.set_position(closest_host.get_position())
 93                    candy = closest_host.remove_candy(choose_heaviest)
 94                    if candy:
 95                        kid.add_candy(candy)
 96                    self._visited_hosts[kid].add(closest_host)
 97            for kid in self._kids:
 98                if kid.is_critical():
 99                    self._victims.add(kid)
100            if self._victims:
101                break
102            if all(len(self._visited_hosts[kid]) == len(self._hosts) for kid in self._kids):
103                break
104
105        return self._victims if self._victims else None
106    
107def choose_heaviest(candies):
108    return max(candies, key=lambda candy: candy.get_mass())

............
----------------------------------------------------------------------
Ran 12 tests in 0.001s

OK

Дискусия
Виктор Бечев
08.11.2023 13:10

Отвъд дребната дори-не-бих-казал-забележка - чист код.
История
Това решение има само една версия.