use crate::card::Card;
use crate::card_sequence::CardSequence;
use crate::enums::EnumSequence as _;
pub(super) struct FoundationSequence(!);
impl CardSequence for FoundationSequence {
fn accepts(current_card: Card, next_card: Card) -> bool {
current_card.suit == next_card.suit && current_card.rank.precedes(next_card.rank)
}
}
#[cfg(test)]
mod test {
use super::FoundationSequence;
use crate::card::{Card, Rank, Suit};
use crate::card_sequence::CardSequence as _;
mod foundation_sequence_accepts {
use assert2::assert;
use rstest::rstest;
use super::*;
#[rstest]
#[case(Rank::Ace, Rank::Two)]
#[case(Rank::Five, Rank::Six)]
#[case(Rank::Ten, Rank::Jack)]
#[case(Rank::Queen, Rank::King)]
fn sequential_same_suit(
#[case] left_rank: Rank,
#[case] right_rank: Rank,
#[values(Suit::Spades, Suit::Clubs, Suit::Hearts, Suit::Diamonds)] suit: Suit,
) {
let left_card = Card {
rank: left_rank,
suit,
};
let right_card = Card {
rank: right_rank,
suit,
};
assert!(FoundationSequence::accepts(left_card, right_card) == true);
}
#[rstest]
#[case(Rank::Ace, Rank::Two)]
#[case(Rank::Five, Rank::Six)]
#[case(Rank::Ten, Rank::Jack)]
#[case(Rank::Queen, Rank::King)]
fn sequential_red_black(
#[case] left_rank: Rank,
#[case] right_rank: Rank,
#[values(Suit::Hearts, Suit::Diamonds)] left_suit: Suit,
#[values(Suit::Spades, Suit::Clubs)] right_suit: Suit,
) {
let left_card = Card {
rank: left_rank,
suit: left_suit,
};
let right_card = Card {
rank: right_rank,
suit: right_suit,
};
assert!(FoundationSequence::accepts(left_card, right_card) == false);
}
#[rstest]
#[case(Rank::Ace, Rank::Two)]
#[case(Rank::Five, Rank::Six)]
#[case(Rank::Ten, Rank::Jack)]
#[case(Rank::Queen, Rank::King)]
fn sequential_black_red(
#[case] left_rank: Rank,
#[case] right_rank: Rank,
#[values(Suit::Spades, Suit::Clubs)] left_suit: Suit,
#[values(Suit::Hearts, Suit::Diamonds)] right_suit: Suit,
) {
let left_card = Card {
rank: left_rank,
suit: left_suit,
};
let right_card = Card {
rank: right_rank,
suit: right_suit,
};
assert!(FoundationSequence::accepts(left_card, right_card) == false);
}
#[rstest]
#[case(Rank::Ace, Rank::Two)]
#[case(Rank::Five, Rank::Six)]
#[case(Rank::Ten, Rank::Jack)]
#[case(Rank::Queen, Rank::King)]
fn sequential_both_red_or_black(
#[case] left_rank: Rank,
#[case] right_rank: Rank,
#[values(
(Suit::Spades, Suit::Clubs),
(Suit::Clubs, Suit::Spades),
(Suit::Hearts, Suit::Diamonds),
(Suit::Diamonds, Suit::Hearts),
)]
suits: (Suit, Suit),
) {
let (left_suit, right_suit) = suits;
let left_card = Card {
rank: left_rank,
suit: left_suit,
};
let right_card = Card {
rank: right_rank,
suit: right_suit,
};
assert!(FoundationSequence::accepts(left_card, right_card) == false);
}
#[rstest]
#[case(Rank::Ace, Rank::Ace)]
#[case(Rank::Two, Rank::Ace)]
#[case(Rank::King, Rank::Ace)]
#[case(Rank::Ace, Rank::Three)]
#[case(Rank::Four, Rank::Four)]
#[case(Rank::Five, Rank::Four)]
#[case(Rank::Six, Rank::Four)]
#[case(Rank::Four, Rank::Six)]
#[case(Rank::King, Rank::King)]
fn nonsequential_all_suits(
#[case] left_rank: Rank,
#[case] right_rank: Rank,
#[values(Suit::Spades, Suit::Clubs, Suit::Hearts, Suit::Diamonds)] left_suit: Suit,
#[values(Suit::Spades, Suit::Clubs, Suit::Hearts, Suit::Diamonds)] right_suit: Suit,
) {
let left_card = Card {
rank: left_rank,
suit: left_suit,
};
let right_card = Card {
rank: right_rank,
suit: right_suit,
};
assert!(FoundationSequence::accepts(left_card, right_card) == false);
}
}
}