# Given an array of five dice with values 1-6, return the best possible hand.
# Here are the hands ranked lowest to highest:
# HandDescription
#"no pair"No pair or better
#"pair"Two dice with the same value
#"two pair"Two different pairs
#"three of a kind"Three dice with the same value
#"small straight"Four consecutive values
#"large straight"Five consecutive values
#"full house"Three of a kind and a pair
#"four of a kind"Four dice with the same value
#"five of a kind"All five dice with the same value
def five_dice(dice):
# 1. Sort array
# 2. Create a dictionary to store counting of numbers
# 3. Iterate the dice array with two pointers
# moving the pointer at the left whenever the straight is interrupted
# we need to store the max straight counter and the current straight counter
# when the straight is interrupted, we need to move the left pointer to the right counter
# and moving the right pointer to the next position from it's current position.
# 4. we need to update the dictionary with the counter of numbers after we move the right pointer
# 5. We must check if there is no straight counter greater than 2 to return small or large straight.
# if the straight counter is not equals to 5, then return small straight.
# Otherwise, return small straight.
# 6. If the dictionary has a single element, return five of a kind
# 7. If the dictionary has two elements, run the following checks:
# 7.a. If any key of the dictionary has four as value, return four of a kind
# 7.b. Otherwise, return full house
# 8. If the dictionary has four elements, return pair
# 9. If the dictionary has three elements, we need to run the following checks:
# 9.a. If one of the keys of the dictionary has three as value, return three of a kind
# 9.b. Otherwise, return two pair
# 10. return no pair as default return
dice.sort()
left_pointer = 0
right_pointer = 1
current_straight = max_straight = 0
dice_length = len(dice)
large_straight_length = 5
minimum_straight_length = 3
numbers_counting = { dice[0]: 1 }
while right_pointer < dice_length:
left_number = dice[left_pointer]
right_number = dice[right_pointer]
counting_duplicates = numbers_counting.setdefault(right_number, 0)
counting_duplicates += 1
numbers_counting[right_number] = counting_duplicates
if left_number + 1 == right_number:
current_straight += 1
else:
if current_straight > max_straight:
max_straight = current_straight
current_straight = 0
left_pointer =+ 1
right_pointer += 1
print(f"max_straight is {max_straight} with dice {dice}")
if max_straight >= minimum_straight_length:
if max_straight == large_straight_length:
return "large straight"
else:
return "small straight"
else:
if len(numbers_counting) == 1:
return "five of a kind"
if len(numbers_counting) == 2:
if next((True for value in numbers_counting.values() if value == 4), False):
return "four of a kind"
else:
return "full house"
if len(numbers_counting) == 4:
return "pair"
if len(numbers_counting) == 3:
if next((True for value in numbers_counting.values() if value == 3), False):
return "three of a kind"
else:
return "two pair"
return "no pair"
result = five_dice([1, 1, 1, 1, 1])
print(f"Is result {result} five of a kind?")
result = five_dice([5, 5, 5, 6, 5])
print(f"Is result {result} four of a kind?")
result = five_dice([1, 3, 4, 6, 2])
print(f"Is result {result} small straight?")