Last active
May 14, 2018 07:51
-
-
Save jakzal/9e2cf64efa5cc90c2b1d1bc13c5132b3 to your computer and use it in GitHub Desktop.
War Card Game in Scala
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
sealed trait Suit | |
sealed case class Hearts() extends Suit { | |
override def toString = "♡" | |
} | |
sealed case class Diamonds() extends Suit { | |
override def toString = "♢" | |
} | |
sealed case class Clubs() extends Suit { | |
override def toString = "♧" | |
} | |
sealed case class Spades() extends Suit { | |
override def toString = "♤" | |
} | |
sealed class Rank(val value: Int) { | |
override def toString = s"${value}" | |
} | |
sealed case class Ace() extends Rank(14) { | |
override def toString = "A" | |
} | |
sealed case class King() extends Rank(13){ | |
override def toString = "K" | |
} | |
sealed case class Queen() extends Rank(12){ | |
override def toString = "Q" | |
} | |
sealed case class Jack() extends Rank(11){ | |
override def toString = "J" | |
} | |
sealed case class Ten() extends Rank(10) | |
sealed case class Nine() extends Rank(9) | |
sealed case class Eight() extends Rank(8) | |
sealed case class Seven() extends Rank(7) | |
sealed case class Six() extends Rank(6) | |
sealed case class Five() extends Rank(5) | |
sealed case class Four() extends Rank(4) | |
sealed case class Three() extends Rank(3) | |
sealed case class Two() extends Rank(2) | |
case class Card(suit: Suit, rank: Rank) { | |
override def toString = rank.toString+suit.toString | |
} | |
type Deck = List[Card] | |
type Hand = List[Card] | |
def suits(): List[Suit] = List(Hearts(), Diamonds(), Clubs(), Spades()) | |
def ranks(): List[Rank] = List(Ace(), King(), Queen(), Jack(), Ten(), Nine(), Eight(), Seven(), Six(), Five(), Four(), Three(), Two()) | |
def deck(): Deck = for ( | |
s <- suits(); | |
r <- ranks() | |
) yield Card(s, r) | |
def shuffle(cards: Deck): Deck = util.Random.shuffle(cards) | |
def divide(cards: Deck): (Hand, Hand) = cards.splitAt(cards.length / 2) | |
sealed trait BattleResult | |
sealed case class Player1Wins(cards: List[Card]) extends BattleResult | |
sealed case class Player2Wins(cards: List[Card]) extends BattleResult | |
sealed case class War(cards: List[Card]) extends BattleResult | |
def score(player1Card: Card, player2Card: Card, previousTurnCards: List[Card] = List()): BattleResult = (player1Card.rank.value - player2Card.rank.value) match { | |
case s if (s == 0) => War(player1Card :: player2Card :: previousTurnCards) | |
case s if (s > 0) => Player1Wins(player1Card :: player2Card :: previousTurnCards) | |
case s if (s < 0) => Player2Wins(player2Card :: player1Card :: previousTurnCards) | |
} | |
def battle(player1Hand: Hand, player2Hand: Hand, previousTurnCards: List[Card] = List()): (Hand, Hand) = (player1Hand, player2Hand) match { | |
case (p1, List()) => (p1, List()) | |
case (List(), p2) => (List(), p2) | |
case (nextCard1 :: remainingCards1, nextCard2 :: remainingCards2) => score(nextCard1, nextCard2, previousTurnCards) match { | |
case Player1Wins(cards) => (remainingCards1 ::: cards, remainingCards2) | |
case Player2Wins(cards) => (remainingCards1, remainingCards2 ::: cards) | |
case War(cards) => battle(remainingCards1, remainingCards2, cards) | |
} | |
} | |
def play(hands: (Hand, Hand)): (Hand, Hand) = hands match { | |
case (h, List()) => (h, List()) | |
case (List(), h) => (List(), h) | |
case (player1: Hand, player2: Hand) => play(battle(player1, player2)) | |
} | |
play(divide(shuffle(deck()))) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment