efficiency improvements. added docs.

This commit is contained in:
Edward Tirado Jr 2025-05-23 13:27:17 -05:00
parent 94b1f06590
commit 79978235b9
3 changed files with 93 additions and 13 deletions

View file

@ -12,6 +12,7 @@ pub enum HandSort {
pub struct Hand {
pub cards: Vec<Card>,
pub card_sort: HandSort,
pub hand_value: u8,
}
impl Hand {
@ -19,6 +20,7 @@ impl Hand {
Hand {
cards: Vec::new(),
card_sort: HandSort::None,
hand_value: 0,
}
}
@ -47,6 +49,7 @@ impl Hand {
self.card_sort = HandSort::Rank;
}
/// Checks all cards and returns total amount of pairs in the hand
fn pair_count(&self) -> u8 {
let mut pairs = 0;
@ -64,6 +67,9 @@ impl Hand {
pairs
}
/// Checks if the current hand has only one pair. \
/// One pair is a hand that contains two cards of one rank and three cards of three
/// other ranks, such as `4♥ 4♠ K♠ 10♦ 5♠`
pub fn has_single_pair(&mut self) -> bool {
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
@ -76,6 +82,9 @@ impl Hand {
false
}
/// Checks if the current hand has exactly two pairs. \
/// Two pair is a hand that contains two cards of one rank, two cards of another rank,
/// and one card of a third rank, such as `J♥ J♣ 4♣ 4♠ 9♥`
pub fn has_two_pair(&mut self) -> bool {
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
@ -88,12 +97,16 @@ impl Hand {
false
}
/// Checks if the current hand has a three of a kind. \
/// Three of a kind is a hand that contains three cards of one rank and
/// two cards of two other ranks, such as `2♦ 2♠ 2♣ K♠ 6♥`
pub fn has_three_of_a_kind(&mut self) -> bool {
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
}
for i in 2..self.cards.len() {
if self.cards[i].rank == self.cards[i - 1].rank && self.cards[i].rank == self.cards[i - 2].rank {
if self.cards[i].rank == self.cards[i - 1].rank &&
self.cards[i].rank == self.cards[i - 2].rank {
return true;
}
}
@ -101,6 +114,9 @@ impl Hand {
false
}
/// Checks if the current hand has a straight. \
/// A straight is a hand that contains five cards of sequential rank,
/// not all the same suit, such as `7♣ 6♠ 5♠ 4♥ 3♥`
pub fn has_straight(&mut self) -> bool {
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
@ -123,6 +139,9 @@ impl Hand {
true
}
/// Checks if the current hand has a flush. \
/// A flush is a hand that contains five cards, all the same suit,
/// and not all of sequential rank, such as `K♣ 10♣ 7♣ 6♣ 4♣`
pub fn has_flush(&self) -> bool {
for i in 1..self.cards.len() {
if self.cards[i].suit != self.cards[i - 1].suit {
@ -133,18 +152,40 @@ impl Hand {
true
}
/// Checks if the current hand has a full house. \
/// A full house is a hand that contains three cards of one
/// rank and two cards of another rank, such as `3♣ 3♠ 3♦ 6♣ 6♥`
pub fn has_full_house(&mut self) -> bool {
if self.has_three_of_a_kind() && self.has_two_pair() {
return true;
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
}
false
let mut has_pair = false;
let mut has_three_of_a_kind = false;
// Check the first two positions for a pair to let the loop check for 2/3 of a kind
if self.cards[0].rank == self.cards[1].rank { has_pair = true; }
for i in 2..self.cards.len() {
if self.cards[i].rank == self.cards[i - 1].rank {
has_pair = true;
}
if self.cards[i].rank == self.cards[i - 1].rank &&
self.cards[i].rank == self.cards[i - 2].rank {
has_three_of_a_kind = true;
}
}
has_pair && has_three_of_a_kind
}
/// Checks if the current hand has a four of a kind. \
/// Four of a kind is a hand that contains four cards of one rank
/// and one card of another rank, such as `9♣ 9♠ 9♦ 9♥ J♥`
pub fn has_four_of_a_kind(&mut self) -> bool {
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
}
for i in 3..self.cards.len() {
if self.cards[i].rank == self.cards[i - 1].rank &&
self.cards[i].rank == self.cards[i - 2].rank &&
@ -157,11 +198,55 @@ impl Hand {
false
}
/// Checks if the current hand has a straight flush. \
/// A straight flush is a hand that contains five cards of sequential rank,
/// all the same suit, such as `Q♥ J♥ 10♥ 9♥ 8♥`
pub fn has_straight_flush(&mut self) -> bool {
self.has_straight() && self.has_flush()
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
}
let mut has_flush = true;
let mut has_straight = true;
let suit = &self.cards[0].suit;
for i in 1..self.cards.len() {
if &self.cards[i].suit != suit {
has_flush = false;
break;
}
if self.cards[i].value != self.cards[i - 1].value + 1 {
has_straight = false;
break;
}
}
has_flush && has_straight
}
/// Checks if the current hand has a royal flush, the best possible hand. \
/// A royal flush is a hand that contains an ace-high straight flush, such as `A♦ K♦ Q♦ J♦ 10♦`
pub fn has_royal_flush(&mut self) -> bool {
self.has_flush() && self.has_straight() && self.cards[0].value == 10
if !matches!(self.card_sort, HandSort::Value) {
self.sort(HandSort::Value);
}
let mut has_flush = true;
let mut has_straight = true;
let suit = &self.cards[0].suit;
for i in 1..self.cards.len() {
if &self.cards[i].suit != suit {
has_flush = false;
break;
}
if self.cards[i].value != self.cards[i - 1].value + 1 {
has_straight = false;
break;
}
}
has_flush && has_straight && self.cards[0].value == 10
}
}

View file

@ -1,13 +1,8 @@
use crate::models::deck::{Card, Deck};
use crate::models::deck::Deck;
use crate::models::hand::Hand;
use crate::models::player::Player;
use std::io;
struct Game {
name: String,
deck: Vec<Card>,
}
pub fn game() {
let mut deck = Deck::new();
deck.shuffle();

View file

@ -17,7 +17,7 @@ mod tests {
}
#[test]
fn test_hand_adds_cards_to_exhasting_hand() {
fn test_hand_draw_adds_cards_to_exhasting_hand() {
let mut deck = Deck::new();
let mut player = Player {
name: String::from("Testy McTestFace"),