Решение на От ливадите до Лас Вегас (и назад) от Никол Казанджиева

Обратно към всички решения

Към профила на Никол Казанджиева

Резултати

  • 5 точки от тестове
  • 0 бонус точки
  • 5 точки общо
  • 7 успешни тест(а)
  • 8 неуспешни тест(а)

Код

import itertools
import random
class Card:
def __init__(self, suit, face):
self._suit = suit
self._face = face
def get_suit(self):
return str(self._suit)
def get_face(self):
return str(self._face)
class Deck:
def __init__(self, face_filter=None):
if face_filter is None:
faces = ['2', '3', '4', '5', '6', '7', '8', '9', '10', 'J', 'Q', 'K', 'A']
self.deck = self.get_deck(faces)
else:
self.deck = self.get_deck(face_filter)
def number_of_cards(self):
return len(self.deck)
def cut(self):
cards_in_deck = self.number_of_cards()
cutting_card = random.randint(1, cards_in_deck)
self.deck = self.deck[cutting_card:] + self.deck[:cutting_card]
def get_cards(self):
return self.deck
def shuffle(self):
random.shuffle(self.deck)
def get_deck(self, face_filter):
suits = ['clubs', 'diamonds', 'hearts', 'spades']
deck = []
for _ in itertools.product(suits, face_filter):
deck.append(_)
return deck
class Player:
def __init__(self):
self.players_deck = Deck([])
def get_cards(self):
return self.players_deck.get_cards()
def add_cards_to_players_deck(self, cards):
self.players_deck.deck.append(cards)

Конструкцията тук е неудачна, защото трябва да кажеш ...deck.deck.... Би било добре да имаш методи в Deck, които да добавят карта, за да го избегнеш. Не е нужно да преправяш сега. Просто споделям мнение.

class Game:
def __init__(self, number_of_players, dealing_direction, dealing_instructions, deck=None):
self.number_of_players = number_of_players
self.dealing_direction = dealing_direction
self.dealing_instructions = dealing_instructions
self.players = []
if not deck:
self.game_deck = Deck()
else:
self.game_deck = deck
for _ in range(number_of_players):
self.players.append(Player())
def get_players(self):
return self.players
def prepare_deck(self):
for player in self.players:
if not player.players_deck.deck:
continue
self.game_deck.deck += player.get_cards()
player.players_deck.deck = []
self.game_deck.shuffle()
self.game_deck.cut()
def get_deck(self):
return self.game_deck
def deal(self, chosen_player):
# this part of the function puts the players in the correct order
correct_players_order = []
count = 0

Не е добра идея да променяш реда на играчите. Ако ти трябва да използваш друг ред, запази го в локална променлива, но не закачай вече установения ред.

for player in self.players:
if player == chosen_player:
break
else:
count += 1
correct_players_order = self.players[count:]+self.players[:count]
if self.dealing_direction == 'rtl': # right to left
correct_players_order.append(self.players[0])
correct_players_order.pop(0)
correct_players_order.reverse()
for number_of_cards in self.dealing_instructions:
for player in self.players:
cards = number_of_cards
while cards > 0:
player.add_cards_to_players_deck(self.game_deck.deck[0])
self.game_deck.deck.pop(0)
cards -= 1
class Belot(Game):
def __init__(self):
super().__init__(4, 'ltr', (2, 3, 3), Deck(['7', '8', '9', '10', 'J', 'Q', 'K', 'A']))
class Poker(Game):
def __init__(self):
super().__init__(9, 'rtl', (1, 1, 1, 1, 1))

Лог от изпълнението

EE...EE..EE..EE
======================================================================
ERROR: test_correct_deck_init (test.TestBelot)
Test initialization with correct deck.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_correct_direction_and_players_deal (test.TestBelot)
Test dealing with correct direction and players.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_init_filtered (test.TestDeck)
Test initialized cards with filter.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_init_regular (test.TestDeck)
Test initialized cards without filter.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_dealing_ltr (test.TestGame)
Test dealing the cards left to right.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_dealing_rtl (test.TestGame)
Test dealing the cards right to left.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_correct_deck_init (test.TestPoker)
Test initialization with correct deck.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

======================================================================
ERROR: test_correct_direction_and_players_deal (test.TestPoker)
Test dealing with correct direction and players.
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/storage/deedee/data/rails/pyfmi-2022/releases/20221115154139/lib/language/python/runner.py", line 67, in thread
    raise result
AttributeError: 'tuple' object has no attribute 'get_suit'

----------------------------------------------------------------------
Ran 15 tests in 0.160s

FAILED (errors=8)

История (2 версии и 9 коментара)

Никол обнови решението на 14.11.2022 16:38 (преди около 2 години)

+import itertools
+import random
+
+
+def get_deck(face_filter):
+ suits = ['clubs', 'diamonds', 'hearts', 'spades']
+ _deck = []
+ for i in itertools.product(suits, face_filter):
+ _deck.append(i)
+ return _deck
+
+
+class Card:
+ def __init__(self, suit, face):
+ self.suit = suit
+ self.face = face
+
+ def get_suit(self):
+ return str(self.suit)
+
+ def get_face(self):
+ return str(self.face)
+
+
+class Deck:
+ def __init__(self, face_filter=None):
+ if face_filter is None:
+ faces = ['2', '3', '4', '5', '6', '7', '8', '9', '10', 'J', 'Q', 'K', 'A']
+ self.deck = get_deck(faces)
+ else:
+ self.deck = get_deck(face_filter)
+
+ def number_of_cards(self):
+ return len(self.deck)
+
+ def cut(self):
+ cards_in_deck = self.number_of_cards()
+ cutting_card = random.randint(1, cards_in_deck)
+ for i in range(0, cutting_card):

Ако няма да използваш променлива, именувай я _, както е по конвенция.
Освен това range(0, x) е същото като range(x).
И последно, само предложение - с list slicing може да стане по-кратко:
self.deck = self.deck[cutting_card:] + self.deck[:cutting_card]

+ tmp = self.deck[0]
+ self.deck.append(tmp)
+ self.deck.pop(0)
+
+ def get_cards(self):
+ return self.deck
+
+ def shuffle(self):
+ random.shuffle(self.deck)
+
+
+class Player:
+ def __init__(self):
+ self.players_deck = Deck([])
+
+ def get_cards(self):
+ return self.players_deck.get_cards()
+
+ def add_cards_to_players_deck(self, cards):
+ self.players_deck.deck.append(cards)

Конструкцията тук е неудачна, защото трябва да кажеш ...deck.deck.... Би било добре да имаш методи в Deck, които да добавят карта, за да го избегнеш. Не е нужно да преправяш сега. Просто споделям мнение.

+
+
+class Game:
+ def __init__(self, number_of_players, dealing_direction, dealing_instructions, deck=Deck()):

deck=Deck() ще се евалюира само веднъж - при дефиниране на класа. Това значи, че ако инстанцирам няколко пъти този клас, всички инстанции ще споделят един и същ deck, т.е. ще стане мармалад.

+ self.number_of_players = number_of_players
+ self.dealing_direction = dealing_direction
+ self.dealing_instructions = dealing_instructions
+ self.players = []
+ self.game_deck = deck
+
+ for i in range(0, number_of_players):
+ self.players.append(Player())
+
+ def get_players(self):
+ return self.players
+
+ def prepare_deck(self):
+ for player in self.players:
+ if not player.players_deck.deck:
+ continue
+ self.game_deck.deck += player.get_cards()
+ player.players_deck.deck = []
+ self.game_deck.shuffle()
+ self.game_deck.cut()
+
+ def get_deck(self):
+ return self.game_deck
+
+ def deal(self, chosen_player):
+ # this part of the function puts the players in the correct order
+ count = 0

Не е добра идея да променяш реда на играчите. Ако ти трябва да използваш друг ред, запази го в локална променлива, но не закачай вече установения ред.

+ for player in self.players:
+ if player == chosen_player:
+ break
+ else:
+ count += 1
+ self.players.append(player)
+ self.players = self.players[count:]
+
+ # left to right
+ if self.dealing_direction == 'ltr':
+ for x in self.dealing_instructions:
+ for player in self.players:
+ cards = x
+ while cards > 0:
+ player.add_cards_to_players_deck(self.game_deck.deck[0])
+ self.game_deck.deck.pop(0)
+ cards -= 1
+ elif self.dealing_direction == 'rtl': # right to left
+ self.players.append(self.players[0])
+ self.players.pop(0)
+ self.players.reverse()
+ for x in self.dealing_instructions:
+ for player in self.players:
+ cards = x
+ while cards > 0:
+ player.add_cards_to_players_deck(self.game_deck.deck[0])
+ self.game_deck.deck.pop(0)
+ cards -= 1
+
+
+class Belot(Game):
+ def __init__(self):
+ super().__init__(4, 'ltr', (2, 3, 3), Deck(['7', '8', '9', '10', 'J', 'Q', 'K', 'A']))
+
+
+class Poker(Game):
+ def __init__(self):
+ super().__init__(9, 'rtl', (1, 1, 1, 1, 1))

Никол обнови решението на 15.11.2022 13:48 (преди около 2 години)

import itertools
import random
-def get_deck(face_filter):
- suits = ['clubs', 'diamonds', 'hearts', 'spades']
- _deck = []
- for i in itertools.product(suits, face_filter):
- _deck.append(i)
- return _deck
-
-
class Card:
def __init__(self, suit, face):
- self.suit = suit
- self.face = face
+ self._suit = suit
+ self._face = face
def get_suit(self):
- return str(self.suit)
+ return str(self._suit)
def get_face(self):
- return str(self.face)
+ return str(self._face)
class Deck:
def __init__(self, face_filter=None):
if face_filter is None:
faces = ['2', '3', '4', '5', '6', '7', '8', '9', '10', 'J', 'Q', 'K', 'A']
- self.deck = get_deck(faces)
+ self.deck = self.get_deck(faces)
else:
- self.deck = get_deck(face_filter)
+ self.deck = self.get_deck(face_filter)
def number_of_cards(self):
return len(self.deck)
def cut(self):
cards_in_deck = self.number_of_cards()
cutting_card = random.randint(1, cards_in_deck)
- for i in range(0, cutting_card):
- tmp = self.deck[0]
- self.deck.append(tmp)
- self.deck.pop(0)
+ self.deck = self.deck[cutting_card:] + self.deck[:cutting_card]
def get_cards(self):
return self.deck
def shuffle(self):
random.shuffle(self.deck)
+ def get_deck(self, face_filter):
+ suits = ['clubs', 'diamonds', 'hearts', 'spades']
+ deck = []
+ for _ in itertools.product(suits, face_filter):
+ deck.append(_)
+ return deck
+
class Player:
def __init__(self):
self.players_deck = Deck([])
def get_cards(self):
return self.players_deck.get_cards()
def add_cards_to_players_deck(self, cards):
self.players_deck.deck.append(cards)
class Game:
- def __init__(self, number_of_players, dealing_direction, dealing_instructions, deck=Deck()):
+ def __init__(self, number_of_players, dealing_direction, dealing_instructions, deck=None):
self.number_of_players = number_of_players
self.dealing_direction = dealing_direction
self.dealing_instructions = dealing_instructions
self.players = []
- self.game_deck = deck
+ if not deck:
+ self.game_deck = Deck()
+ else:
+ self.game_deck = deck
- for i in range(0, number_of_players):
+ for _ in range(number_of_players):
self.players.append(Player())
def get_players(self):
return self.players
def prepare_deck(self):
for player in self.players:
if not player.players_deck.deck:
continue
self.game_deck.deck += player.get_cards()
player.players_deck.deck = []
self.game_deck.shuffle()
self.game_deck.cut()
def get_deck(self):
return self.game_deck
def deal(self, chosen_player):
# this part of the function puts the players in the correct order
+ correct_players_order = []
count = 0
for player in self.players:
if player == chosen_player:
break
else:
count += 1
- self.players.append(player)
- self.players = self.players[count:]
+ correct_players_order = self.players[count:]+self.players[:count]
- # left to right
- if self.dealing_direction == 'ltr':
- for x in self.dealing_instructions:
- for player in self.players:
- cards = x
- while cards > 0:
- player.add_cards_to_players_deck(self.game_deck.deck[0])
- self.game_deck.deck.pop(0)
- cards -= 1
- elif self.dealing_direction == 'rtl': # right to left
- self.players.append(self.players[0])
- self.players.pop(0)
- self.players.reverse()
- for x in self.dealing_instructions:
- for player in self.players:
- cards = x
- while cards > 0:
- player.add_cards_to_players_deck(self.game_deck.deck[0])
- self.game_deck.deck.pop(0)
- cards -= 1
+ if self.dealing_direction == 'rtl': # right to left
+ correct_players_order.append(self.players[0])
+ correct_players_order.pop(0)
+ correct_players_order.reverse()
+
+ for number_of_cards in self.dealing_instructions:
+ for player in self.players:
+ cards = number_of_cards
+ while cards > 0:
+ player.add_cards_to_players_deck(self.game_deck.deck[0])
+ self.game_deck.deck.pop(0)
+ cards -= 1
class Belot(Game):
def __init__(self):
super().__init__(4, 'ltr', (2, 3, 3), Deck(['7', '8', '9', '10', 'J', 'Q', 'K', 'A']))
class Poker(Game):
def __init__(self):
super().__init__(9, 'rtl', (1, 1, 1, 1, 1))