Домашни > Предизборно ООП > Решения > Решението на Боян Байданов

Резултати
7 точки от тестове
-7 точки от учител

0 точки общо

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

  1class Currency:
  2    def __init__(self, name, rate):
  3        self.name = name
  4        self.rate = rate
  5
  6    def __eq__(self, other):
  7        if not isinstance(other, Currency):
  8            return NotImplemented
  9        return self.name == other.name and self.rate == other.rate
 10
 11    def __repr__(self):
 12        return f"Currency({self.name!r}, {self.rate})"
 13
 14
 15class PoliticalParty:
 16    def __init__(self, name, motto, members=None, preferred_currency=None):
 17        self.name = name
 18        self._motto = motto
 19        self.members = members or []
 20        self.preferred_currency = preferred_currency
 21
 22    @property
 23    def motto(self):
 24        return self._motto
 25
 26    @motto.setter
 27    def motto(self, value):
 28        raise AttributeError("Девизът не може да бъде променян!")
 29
 30    def convert_currency_to_voters(self, amount, currency):
 31        votes = int(amount / currency.rate)
 32        if self.preferred_currency and currency == self.preferred_currency:
 33            votes *= 2
 34        return votes
 35
 36    def __str__(self):
 37        return self.name
 38
 39    def __repr__(self):
 40        return f"PoliticalParty({self.name!r})"
 41
 42    def __add__(self, other):
 43        if isinstance(other, PoliticalParty):
 44            return Coalition(self, other)
 45        if isinstance(other, Coalition):
 46            return Coalition(self, *other._parties)
 47        return NotImplemented
 48
 49
 50class Coalition:
 51    def __init__(self, *parties):
 52        # Each argument may be a PoliticalParty or another Coalition;
 53        # flatten everything into an ordered list of PoliticalParty objects.
 54        self._parties = []
 55        for item in parties:
 56            if isinstance(item, PoliticalParty):
 57                self._parties.append(item)
 58            elif isinstance(item, Coalition):
 59                self._parties.extend(item._parties)
 60            else:
 61                raise TypeError(f"Expected PoliticalParty or Coalition, got {type(item)}")
 62
 63    @property
 64    def members(self):
 65        return {party.name: list(party.members) for party in self._parties}
 66
 67    def __str__(self):
 68        return "-".join(party.name for party in self._parties)
 69
 70    def __repr__(self):
 71        return f"Coalition({str(self)!r})"
 72
 73    def __add__(self, other):
 74        if isinstance(other, PoliticalParty):
 75            return Coalition(*self._parties, other)
 76        if isinstance(other, Coalition):
 77            return Coalition(*self._parties, *other._parties)
 78        return NotImplemented
 79
 80
 81class Elections:
 82    # Class-level registry: {year: Elections instance}
 83    _registry = {}
 84
 85    def __init__(self, year):
 86        self.year = year
 87        # {str(party_or_coalition): {"entity": ..., "votes": int}}
 88        self._entries = {}
 89        Elections._registry[year] = self
 90
 91    def _key(self, entity):
 92        return str(entity)
 93
 94    def register_party_or_coalition(self, entity):
 95        key = self._key(entity)
 96        if key not in self._entries:
 97            self._entries[key] = {"entity": entity, "votes": 0}
 98
 99    def vote(self, entity):
100        key = self._key(entity)
101        if key not in self._entries:
102            raise ValueError(f"{entity!r} is not registered in these elections")
103        self._entries[key]["votes"] += 1
104
105    def rig_elections(self, entity, amount, currency):
106        key = self._key(entity)
107        if key not in self._entries:
108            raise ValueError(f"{entity!r} is not registered in these elections")
109        entity_obj = self._entries[key]["entity"]
110
111        # For a coalition: pick the member party that yields the most votes for
112        # this currency (a party with a matching preferred_currency gets a 2x bonus),
113        # then credit the winning count to the coalition.
114        if isinstance(entity_obj, Coalition):
115            best_votes = 0
116            for party in entity_obj._parties:
117                votes = party.convert_currency_to_voters(amount, currency)
118                if votes > best_votes:
119                    best_votes = votes
120            self._entries[key]["votes"] += best_votes
121        else:
122            # It's a PoliticalParty
123            self._entries[key]["votes"] += entity_obj.convert_currency_to_voters(amount, currency)
124
125    def get_results(self):
126        return {key: data["votes"] for key, data in self._entries.items()}
127
128    @classmethod
129    def get_results_by_year(cls, year):
130        if year not in cls._registry:
131            return {}
132        return cls._registry[year].get_results()
133
134
135# ---------------------------------------------------------------------------
136# Quick smoke tests — run with: python elections.py
137# ---------------------------------------------------------------------------
138if __name__ == "__main__":
139    # Currency equality
140    kebapcheta      = Currency("кебапчета", 15)
141    pak_kebapcheta  = Currency("кебапчета", 15)
142    gadni_kebapcheta = Currency("кебапчета", 35)
143    evra            = Currency("евро", 35)
144
145    assert kebapcheta == pak_kebapcheta,       "Should be equal"
146    assert not (kebapcheta == gadni_kebapcheta), "Should differ"
147    assert not (gadni_kebapcheta == evra),       "Should differ"
148    print("Currency equality: OK")
149
150    # Motto read-only
151    GERB_test = PoliticalParty("ГЕРБ", "Ту-тууу!")
152    assert GERB_test.motto == "Ту-тууу!"
153    try:
154        GERB_test.motto = "Нещо друго"
155        assert False, "Should have raised"
156    except AttributeError:
157        pass
158    print("Motto read-only: OK")
159
160    # convert_currency_to_voters
161    leva      = Currency("левчета", 50)
162    SDS_test  = PoliticalParty("СДС", "Ние също сме шокирани...")
163    greatness = PoliticalParty("Величие", "Не на еврото!", preferred_currency=leva)
164    assert SDS_test.convert_currency_to_voters(100, leva) == 2
165    assert greatness.convert_currency_to_voters(100, leva) == 4
166
167    kebapcheta2 = Currency("кебапчета", 15)
168    DPS = PoliticalParty("ДПС", "КТБ по КТБ...", preferred_currency=kebapcheta2)
169    assert DPS.convert_currency_to_voters(50, kebapcheta2) == 6
170    print("convert_currency_to_voters: OK")
171
172    # Coalition basics
173    yes_Bulgaria = PoliticalParty("Да, България", "Ще щурмуваме...",
174                                  members=["Божо", "Ивайло Мирчев"])
175    DSB = PoliticalParty("ДСБ", "Помните ли Иван Костов?",
176                         members=["Не-Иван-Костов", "Пак не е Иван Костов"])
177    DB = Coalition(yes_Bulgaria, DSB)
178    assert DB.members == {
179        "Да, България": ["Божо", "Ивайло Мирчев"],
180        "ДСБ": ["Не-Иван-Костов", "Пак не е Иван Костов"],
181    }
182    print("Coalition.members: OK")
183
184    # Coalition + Party
185    PP = PoliticalParty("ПП", "Не сме сигурни...", members=["Асенката"])
186    PPDB = DB + PP
187    assert list(PPDB.members.keys()) == ["Да, България", "ДСБ", "ПП"]
188    assert str(PPDB) == "Да, България-ДСБ-ПП"
189    print("Coalition + Party: OK")
190
191    # Coalition + Coalition
192    GERB2 = PoliticalParty("ГЕРБ", "Ту-тууу!", members=["Бат'", "Бойко", "и", "сам", "стига"])
193    SDS2  = PoliticalParty("СДС",  "Ние също...", members=["Румен, ама не Радев"])
194    GERB_SDS = GERB2 + SDS2
195    OMG = DB + GERB_SDS
196    assert list(OMG.members.keys()) == ["Да, България", "ДСБ", "ГЕРБ", "СДС"]
197    print("Coalition + Coalition: OK")
198
199    # Elections full example
200    elections_2026 = Elections(2026)
201
202    BSP = PoliticalParty("БСП", "Ще вдигнем пенсиите и тази година!",
203                         members=["Крум Еди-Кой-Си", "Атанас Еди-Кой-Си", "Онзи другия"])
204    elections_2026.register_party_or_coalition(BSP)
205
206    gold_bars = Currency("мини-златни кюлчета", 0.2)
207    GERB3 = PoliticalParty("ГЕРБ", "Ту-тууу!",
208                           members=["Бат'", "Бойко", "и", "сам", "стига"],
209                           preferred_currency=gold_bars)
210    SDS3  = PoliticalParty("СДС", "Ние също сме шокирани...",
211                           members=["Румен, ама не Радев"])
212    GERB_SDS2 = GERB3 + SDS3
213
214    elections_2026.register_party_or_coalition(GERB_SDS2)
215    elections_2026.vote(BSP)
216    elections_2026.rig_elections(GERB_SDS2, 1, gold_bars)
217
218    results = elections_2026.get_results()
219    assert results == {"БСП": 1, "ГЕРБ-СДС": 10}, f"Got: {results}"
220    print("Elections full example: OK")
221
222    print("\nВсички тестове минаха успешно!")

.....................
----------------------------------------------------------------------
Ran 21 tests in 0.001s

OK

Дискусия
Боян Байданов
25.03.2026 13:05

Смятам че решението се е получило добре, защото изискванията на задачата са много добре разписани. При по-неясни условия опита ми показва, че бота няма да се справи толкова добре.
Виктор Бечев
25.03.2026 12:40

Отвъд горните коментари - притеснително приличен код. :grin:
Виктор Бечев
25.03.2026 12:35

Мерси за чесността, точки няма да получиш, ама на теб така или иначе за точките ти е все тая. ☺️
Боян Байданов
24.03.2026 22:41

Малко нямах време и го направих с Claude Code. Напълно ок съм да не получа точки или човешка проверка, а само да видя дали ще мине автоматичните тестове.
История
Това решение има само една версия.