Решение на Четвърта задача от Адриана Стефанова

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

Към профила на Адриана Стефанова

Резултати

  • 5 точки от тестове
  • 1 отнета точка
  • 4 точки общо
  • 48 успешни тест(а)
  • 9 неуспешни тест(а)

Код

module SuitsConstant
SUITS = [:spades, :hearts, :diamonds, :clubs]
end
module WarConstants
include SuitsConstant
RANKS = [2, 3, 4, 5, 6, 7, 8, 9, 10, :jack, :queen, :king, :ace]
end
module BeloteConstants
include SuitsConstant
RANKS = [7, 8, 9, :jack, :queen, :king, 10, :ace]
end
module SixtySixConstants
include SuitsConstant
RANKS = [9, :jack, :queen, :king, 10, :ace]
end
class Card
include WarConstants
attr_reader :rank
attr_reader :suit
def initialize(rank, suit)
initialize_card(RANKS, rank, suit)
end
def to_s
capitalize_first_letter(rank) << " of " << capitalize_first_letter(suit)
end
def ==(another)
self.class == another.class && self.rank == another.rank &&
self.suit == another.suit
end
def <=>(another)
compare(another, RANKS)
end
private
def initialize_card(ranks, rank, suit)
if ranks.include?(rank) && SUITS.include?(suit)
@rank, @suit = rank, suit
else
raise "Invalid card"
end
end
def capitalize_first_letter(word)
word.to_s.split.map(&:capitalize).join(' ')
end
def compare(another, ranks)
if ranks.find_index(self.rank) < ranks.find_index(another.rank)
compare_smaller_rank(self.suit, another.suit)
elsif ranks.find_index(self.rank) > ranks.find_index(another.rank)
compare_larger_rank(self.suit, another.suit)
else
compare_equal_rank(self.suit, another.suit)
end
end
def compare_smaller_rank(self_suit, another_suit)
if SUITS.find_index(self_suit) >= SUITS.find_index(another_suit)
1
elsif SUITS.find_index(self_suit) < SUITS.find_index(another_suit)
-1
end
end
def compare_larger_rank(self_suit, another_suit)
if SUITS.find_index(self_suit) <= SUITS.find_index(another_suit)
-1
elsif SUITS.find_index(self_suit) > SUITS.find_index(another_suit)
1
end
end
def compare_equal_rank(self_suit, another_suit)
if SUITS.find_index(self_suit) < SUITS.find_index(another_suit)
-1
elsif SUITS.find_index(self_suit) > SUITS.find_index(another_suit)
1
else
0
end
end
end
class BeloteCard < Card
include BeloteConstants
def initialize(rank, suit)
initialize_card(RANKS, rank, suit)
end
def <=>(another)
compare(another, RANKS)
end
end
class SixtySixCard < Card
include SixtySixConstants
def initialize(rank, suit)
initialize_card(RANKS, rank, suit)
end
def <=>(another)
compare(another, RANKS)
end
end
class Hand
attr_accessor :hand
def initialize(cards)
@hand = cards
end
def allow_face_up?
@hand.size <= 3
end
def play_card
@hand.pop
end
def size
@hand.size
end
def to_s
@hand.to_s
end
end
class BeloteHand < Hand
include BeloteConstants
def highest_of_suit(suit)
max = @hand.first
@hand.select{|card|
card.suit == suit
}.each{|card_of_suit|
if RANKS.find_index(max.rank) < RANKS.find_index(card_of_suit.rank)
max = card_of_suit
end
}
max
end
def belote?
@hand.group_by{|card| card.suit}.
each{|all_of_suit|
all_of_suit.shift
if (all_of_suit.include?(:king) && all_of_suit.include?(:queen))
return true
end
}
false
end
def tierce?
consequential?(3)
end
def quarte?
consequential?(4)
end
def quint?
consequential?(5)
end
def carre_of_jacks?
carre?(:jack)
end
def carre_of_nines?
carre?(9)
end
def carre_of_aces?
carre?(:ace)
end
private
def consequential?(number)
suits = @hand.group_by{ |card_in_hand|
card_in_hand.suit
}
suits.each { |all_of_suit|
all_of_suit.shift
if loop_all_of_suit(number, all_of_suit)
return true
end
}
false
end
def loop_all_of_suit(number, all_of_suit)
all_of_suit.each{ |set|
set.sort
if find_match(number, set)
return true
end
}
false
end
def find_match(number, set)
set.each_cons(number){|sorted_set|
if has_match(number, sorted_set)
return true
end
}
false
end
def has_match(number, sorted_set)
RANKS.each_cons(number){|ranks|
if ((ranks & sorted_set.map{|card| card.rank}).size == 3)
return true
end
}
false
end
def carre?(rank)
[BeloteCard.new(rank, :spades), BeloteCard.new(rank, :diamonds),
BeloteCard.new(rank, :hearts), BeloteCard.new(rank, :clubs)].all?{|rank|
@hand.include?(rank)
}
end
end
class SixtySixHand < Hand
include SixtySixConstants
def twenty?(trump_suit)
SUITS.each{|suit|
if(suit != trump_suit && @hand.include?(SixtySixCard.new(:queen, suit)) &&
@hand.include?(SixtySixCard.new(:king, suit)))
return true
end
}
false
end
def forty?(trump_suit)
@hand.include?(SixtySixCard.new(:queen, trump_suit)) &&
@hand.include?(SixtySixCard.new(:king, trump_suit))
end
end
class Deck
include Enumerable
include SuitsConstant
attr_reader :size
attr_accessor :cards
def initialize(cards = [])
@cards = cards
end
def iterate(suits, ranks, *game)
if @cards == []
each_suit(suits, ranks, *game){ |card| yield card}
else
@cards.each{ |card|
yield card
}
end
end
def draw_top_card
@cards.shift
end
def draw_bottom_card
@cards.pop
end
def top_card
@cards.first
end
def bottom_card
@cards.last
end
def shuffle
@cards.shuffle!
end
def sort
@cards.sort!
end
def to_s
result = ""
@cards.each{|card|
result << card.to_s << "\n"
}
result
end
def size
@cards.size
end
private
def each_suit(suits, ranks, *game)
suits.each{ |suit|
each_rank(ranks, suit, *game){ |card| yield card}
}
end
def each_rank(ranks, suit, *game)
ranks.each { |rank|
card = instantiate_card(rank, suit, *game)
@cards << card
yield card
}
end
def instantiate_card(rank, suit, *game)
if game == [:belote]
BeloteCard.new(rank, suit)
elsif game == [:sixty_six]
SixtySixCard.new(rank, suit)
else
Card.new(rank, suit)
end
end
end
class WarDeck < Deck
include WarConstants
def initialize(cards = [])
super
self.each{ |card| }
end
def each(&block)
iterate(SUITS, RANKS){ |card| yield card }
end
def deal
Hand.new(@cards.shift(26))
end
end
class BeloteDeck < Deck
include BeloteConstants
def initialize(cards = [])
super
self.each{ |card| }
end
def each(&block)
iterate(SUITS, RANKS, :belote){ |card| yield card }
end
def deal
BeloteHand.new(@cards.shift(8))
end
end
class SixtySixDeck < Deck
include SixtySixConstants
def initialize(cards = [])
super
self.each{ |card| }
end
def each(&block)
iterate(SUITS, RANKS, :sixty_six){ |card| yield card }
end
def deal
SixtySixHand.new(@cards.shift(6))
end
end

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

.................F.........FF.F......F.F.F..F.........F..

Failures:

  1) BeloteDeck behaves like a deck fills the deck if no initialize parameters are given
     Failure/Error: expect(deck.to_a).to match_array all_available_cards
       expected collection contained:  [#<Card:0x007faf34309810 @rank=:ace, @suit=:spades>, #<Card:0x007faf343098b0 @rank=:king, @suit=:spades>, #<Card:0x007faf34309928 @rank=:queen, @suit=:spades>, #<Card:0x007faf34309978 @rank=:jack, @suit=:spades>, #<Card:0x007faf34309860 @rank=10, @suit=:spades>, #<Card:0x007faf343099f0 @rank=9, @suit=:spades>, #<Card:0x007faf34309a40 @rank=8, @suit=:spades>, #<Card:0x007faf34309a90 @rank=7, @suit=:spades>, #<Card:0x007faf34309ae0 @rank=:ace, @suit=:hearts>, #<Card:0x007faf34309b80 @rank=:king, @suit=:hearts>, #<Card:0x007faf34309bd0 @rank=:queen, @suit=:hearts>, #<Card:0x007faf34309c20 @rank=:jack, @suit=:hearts>, #<Card:0x007faf34309b30 @rank=10, @suit=:hearts>, #<Card:0x007faf34309c70 @rank=9, @suit=:hearts>, #<Card:0x007faf34309cc0 @rank=8, @suit=:hearts>, #<Card:0x007faf34309d10 @rank=7, @suit=:hearts>, #<Card:0x007faf34309db0 @rank=:ace, @suit=:diamonds>, #<Card:0x007faf34309e50 @rank=:king, @suit=:diamonds>, #<Card:0x007faf34309ea0 @rank=:queen, @suit=:diamonds>, #<Card:0x007faf34309ef0 @rank=:jack, @suit=:diamonds>, #<Card:0x007faf34309e00 @rank=10, @suit=:diamonds>, #<Card:0x007faf34309f40 @rank=9, @suit=:diamonds>, #<Card:0x007faf34309f90 @rank=8, @suit=:diamonds>, #<Card:0x007faf3430a008 @rank=7, @suit=:diamonds>, #<Card:0x007faf3430a058 @rank=:ace, @suit=:clubs>, #<Card:0x007faf3430a0f8 @rank=:king, @suit=:clubs>, #<Card:0x007faf3430a170 @rank=:queen, @suit=:clubs>, #<Card:0x007faf3430a1c0 @rank=:jack, @suit=:clubs>, #<Card:0x007faf3430a0a8 @rank=10, @suit=:clubs>, #<Card:0x007faf3430a2d8 @rank=9, @suit=:clubs>, #<Card:0x007faf3430a328 @rank=8, @suit=:clubs>, #<Card:0x007faf3430a3a0 @rank=7, @suit=:clubs>]
       actual collection contained:    [#<BeloteCard:0x007faf343197d8 @rank=:ace, @suit=:spades>, #<BeloteCard:0x007faf34319918 @rank=10, @suit=:spades>, #<BeloteCard:0x007faf343199e0 @rank=:king, @suit=:spades>, #<BeloteCard:0x007faf34319b70 @rank=:queen, @suit=:spades>, #<BeloteCard:0x007faf34319d28 @rank=:jack, @suit=:spades>, #<BeloteCard:0x007faf34319e18 @rank=9, @suit=:spades>, #<BeloteCard:0x007faf34319fd0 @rank=8, @suit=:spades>, #<BeloteCard:0x007faf3431a390 @rank=7, @suit=:spades>, #<BeloteCard:0x007faf34318978 @rank=:ace, @suit=:hearts>, #<BeloteCard:0x007faf34318a68 @rank=10, @suit=:hearts>, #<BeloteCard:0x007faf34318c70 @rank=:king, @suit=:hearts>, #<BeloteCard:0x007faf34318e28 @rank=:queen, @suit=:hearts>, #<BeloteCard:0x007faf34318f18 @rank=:jack, @suit=:hearts>, #<BeloteCard:0x007faf34319120 @rank=9, @suit=:hearts>, #<BeloteCard:0x007faf343192d8 @rank=8, @suit=:hearts>, #<BeloteCard:0x007faf34319440 @rank=7, @suit=:hearts>, #<BeloteCard:0x007faf3430bae8 @rank=:ace, @suit=:diamonds>, #<BeloteCard:0x007faf3430bbb0 @rank=10, @suit=:diamonds>, #<BeloteCard:0x007faf3430bd90 @rank=:king, @suit=:diamonds>, #<BeloteCard:0x007faf34318b30 @rank=:queen, @suit=:diamonds>, #<BeloteCard:0x007faf343180e0 @rank=:jack, @suit=:diamonds>, #<BeloteCard:0x007faf34318478 @rank=9, @suit=:diamonds>, #<BeloteCard:0x007faf34318568 @rank=8, @suit=:diamonds>, #<BeloteCard:0x007faf34318630 @rank=7, @suit=:diamonds>, #<BeloteCard:0x007faf3430ad28 @rank=:ace, @suit=:clubs>, #<BeloteCard:0x007faf3430aee0 @rank=10, @suit=:clubs>, #<BeloteCard:0x007faf3430afa8 @rank=:king, @suit=:clubs>, #<BeloteCard:0x007faf3430b070 @rank=:queen, @suit=:clubs>, #<BeloteCard:0x007faf3430b228 @rank=:jack, @suit=:clubs>, #<BeloteCard:0x007faf3430b318 @rank=9, @suit=:clubs>, #<BeloteCard:0x007faf3430b480 @rank=8, @suit=:clubs>, #<BeloteCard:0x007faf3430b6d8 @rank=7, @suit=:clubs>]
       the missing elements were:      [#<Card:0x007faf34309810 @rank=:ace, @suit=:spades>, #<Card:0x007faf343098b0 @rank=:king, @suit=:spades>, #<Card:0x007faf34309928 @rank=:queen, @suit=:spades>, #<Card:0x007faf34309978 @rank=:jack, @suit=:spades>, #<Card:0x007faf34309860 @rank=10, @suit=:spades>, #<Card:0x007faf343099f0 @rank=9, @suit=:spades>, #<Card:0x007faf34309a40 @rank=8, @suit=:spades>, #<Card:0x007faf34309a90 @rank=7, @suit=:spades>, #<Card:0x007faf34309ae0 @rank=:ace, @suit=:hearts>, #<Card:0x007faf34309b80 @rank=:king, @suit=:hearts>, #<Card:0x007faf34309bd0 @rank=:queen, @suit=:hearts>, #<Card:0x007faf34309c20 @rank=:jack, @suit=:hearts>, #<Card:0x007faf34309b30 @rank=10, @suit=:hearts>, #<Card:0x007faf34309c70 @rank=9, @suit=:hearts>, #<Card:0x007faf34309cc0 @rank=8, @suit=:hearts>, #<Card:0x007faf34309d10 @rank=7, @suit=:hearts>, #<Card:0x007faf34309db0 @rank=:ace, @suit=:diamonds>, #<Card:0x007faf34309e50 @rank=:king, @suit=:diamonds>, #<Card:0x007faf34309ea0 @rank=:queen, @suit=:diamonds>, #<Card:0x007faf34309ef0 @rank=:jack, @suit=:diamonds>, #<Card:0x007faf34309e00 @rank=10, @suit=:diamonds>, #<Card:0x007faf34309f40 @rank=9, @suit=:diamonds>, #<Card:0x007faf34309f90 @rank=8, @suit=:diamonds>, #<Card:0x007faf3430a008 @rank=7, @suit=:diamonds>, #<Card:0x007faf3430a058 @rank=:ace, @suit=:clubs>, #<Card:0x007faf3430a0f8 @rank=:king, @suit=:clubs>, #<Card:0x007faf3430a170 @rank=:queen, @suit=:clubs>, #<Card:0x007faf3430a1c0 @rank=:jack, @suit=:clubs>, #<Card:0x007faf3430a0a8 @rank=10, @suit=:clubs>, #<Card:0x007faf3430a2d8 @rank=9, @suit=:clubs>, #<Card:0x007faf3430a328 @rank=8, @suit=:clubs>, #<Card:0x007faf3430a3a0 @rank=7, @suit=:clubs>]
       the extra elements were:        [#<BeloteCard:0x007faf343197d8 @rank=:ace, @suit=:spades>, #<BeloteCard:0x007faf34319918 @rank=10, @suit=:spades>, #<BeloteCard:0x007faf343199e0 @rank=:king, @suit=:spades>, #<BeloteCard:0x007faf34319b70 @rank=:queen, @suit=:spades>, #<BeloteCard:0x007faf34319d28 @rank=:jack, @suit=:spades>, #<BeloteCard:0x007faf34319e18 @rank=9, @suit=:spades>, #<BeloteCard:0x007faf34319fd0 @rank=8, @suit=:spades>, #<BeloteCard:0x007faf3431a390 @rank=7, @suit=:spades>, #<BeloteCard:0x007faf34318978 @rank=:ace, @suit=:hearts>, #<BeloteCard:0x007faf34318a68 @rank=10, @suit=:hearts>, #<BeloteCard:0x007faf34318c70 @rank=:king, @suit=:hearts>, #<BeloteCard:0x007faf34318e28 @rank=:queen, @suit=:hearts>, #<BeloteCard:0x007faf34318f18 @rank=:jack, @suit=:hearts>, #<BeloteCard:0x007faf34319120 @rank=9, @suit=:hearts>, #<BeloteCard:0x007faf343192d8 @rank=8, @suit=:hearts>, #<BeloteCard:0x007faf34319440 @rank=7, @suit=:hearts>, #<BeloteCard:0x007faf3430bae8 @rank=:ace, @suit=:diamonds>, #<BeloteCard:0x007faf3430bbb0 @rank=10, @suit=:diamonds>, #<BeloteCard:0x007faf3430bd90 @rank=:king, @suit=:diamonds>, #<BeloteCard:0x007faf34318b30 @rank=:queen, @suit=:diamonds>, #<BeloteCard:0x007faf343180e0 @rank=:jack, @suit=:diamonds>, #<BeloteCard:0x007faf34318478 @rank=9, @suit=:diamonds>, #<BeloteCard:0x007faf34318568 @rank=8, @suit=:diamonds>, #<BeloteCard:0x007faf34318630 @rank=7, @suit=:diamonds>, #<BeloteCard:0x007faf3430ad28 @rank=:ace, @suit=:clubs>, #<BeloteCard:0x007faf3430aee0 @rank=10, @suit=:clubs>, #<BeloteCard:0x007faf3430afa8 @rank=:king, @suit=:clubs>, #<BeloteCard:0x007faf3430b070 @rank=:queen, @suit=:clubs>, #<BeloteCard:0x007faf3430b228 @rank=:jack, @suit=:clubs>, #<BeloteCard:0x007faf3430b318 @rank=9, @suit=:clubs>, #<BeloteCard:0x007faf3430b480 @rank=8, @suit=:clubs>, #<BeloteCard:0x007faf3430b6d8 @rank=7, @suit=:clubs>]
     Shared Example Group: "a deck" called from /tmp/d20151112-27349-5h228p/spec.rb:191
     # /tmp/d20151112-27349-5h228p/spec.rb:18:in `block (2 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  2) BeloteDeck hand #highest_of_suit returns the strongest card of the specified suit
     Failure/Error: expect(hand.highest_of_suit(:spades)).to eq Card.new(:king, :spades)
       
       expected: #<Card:0x007faf3421c290 @rank=:king, @suit=:spades>
            got: #<Card:0x007faf3421e130 @rank=:ace, @suit=:clubs>
       
       (compared using ==)
       
       Diff:
       @@ -1,2 +1,2 @@
       -#<Card:0x007faf3421c290 @rank=:king, @suit=:spades>
       +#<Card:0x007faf3421e130 @rank=:ace, @suit=:clubs>
     # /tmp/d20151112-27349-5h228p/spec.rb:233:in `block (4 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  3) BeloteDeck hand #belote? returns true if there is a king and a queen of the same suit
     Failure/Error: expect(hand.belote?).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     # /tmp/d20151112-27349-5h228p/spec.rb:251:in `block (4 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  4) BeloteDeck hand #tierce? with tierce returns true for cards with names
     Failure/Error: expect(hand.tierce?).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     # /tmp/d20151112-27349-5h228p/spec.rb:284:in `block (5 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  5) BeloteDeck hand #carre_of_jacks? behaves like carre-checking method returns true when there is a carre
     Failure/Error: expect(hand.public_send(method)).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     Shared Example Group: "carre-checking method" called from /tmp/d20151112-27349-5h228p/spec.rb:386
     # /tmp/d20151112-27349-5h228p/spec.rb:86:in `block (2 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  6) BeloteDeck hand #carre_of_nines? behaves like carre-checking method returns true when there is a carre
     Failure/Error: expect(hand.public_send(method)).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     Shared Example Group: "carre-checking method" called from /tmp/d20151112-27349-5h228p/spec.rb:390
     # /tmp/d20151112-27349-5h228p/spec.rb:86:in `block (2 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  7) BeloteDeck hand #carre_of_aces? behaves like carre-checking method returns true when there is a carre
     Failure/Error: expect(hand.public_send(method)).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     Shared Example Group: "carre-checking method" called from /tmp/d20151112-27349-5h228p/spec.rb:394
     # /tmp/d20151112-27349-5h228p/spec.rb:86:in `block (2 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  8) SixtySixDeck behaves like a deck fills the deck if no initialize parameters are given
     Failure/Error: expect(deck.to_a).to match_array all_available_cards
       expected collection contained:  [#<Card:0x007faf33eb6b28 @rank=:ace, @suit=:spades>, #<Card:0x007faf33eb6c40 @rank=:king, @suit=:spades>, #<Card:0x007faf33eb6ce0 @rank=:queen, @suit=:spades>, #<Card:0x007faf33eb6d80 @rank=:jack, @suit=:spades>, #<Card:0x007faf33eb6b78 @rank=10, @suit=:spades>, #<Card:0x007faf33eb6ee8 @rank=9, @suit=:spades>, #<Card:0x007faf33eb6fb0 @rank=:ace, @suit=:hearts>, #<Card:0x007faf33eb70f0 @rank=:king, @suit=:hearts>, #<Card:0x007faf33eb7190 @rank=:queen, @suit=:hearts>, #<Card:0x007faf33eb7230 @rank=:jack, @suit=:hearts>, #<Card:0x007faf33eb7050 @rank=10, @suit=:hearts>, #<Card:0x007faf33eb7370 @rank=9, @suit=:hearts>, #<Card:0x007faf33eb7410 @rank=:ace, @suit=:diamonds>, #<Card:0x007faf33eb7578 @rank=:king, @suit=:diamonds>, #<Card:0x007faf33eb7618 @rank=:queen, @suit=:diamonds>, #<Card:0x007faf33eb7668 @rank=:jack, @suit=:diamonds>, #<Card:0x007faf33eb7488 @rank=10, @suit=:diamonds>, #<Card:0x007faf33eb77d0 @rank=9, @suit=:diamonds>, #<Card:0x007faf33eb7820 @rank=:ace, @suit=:clubs>, #<Card:0x007faf33eb7960 @rank=:king, @suit=:clubs>, #<Card:0x007faf33eb79d8 @rank=:queen, @suit=:clubs>, #<Card:0x007faf33eb7a78 @rank=:jack, @suit=:clubs>, #<Card:0x007faf33eb78e8 @rank=10, @suit=:clubs>, #<Card:0x007faf33eb7b40 @rank=9, @suit=:clubs>]
       actual collection contained:    [#<SixtySixCard:0x007faf33ed44e8 @rank=:ace, @suit=:spades>, #<SixtySixCard:0x007faf33ed46a0 @rank=10, @suit=:spades>, #<SixtySixCard:0x007faf33ed47e0 @rank=:king, @suit=:spades>, #<SixtySixCard:0x007faf33ed48f8 @rank=:queen, @suit=:spades>, #<SixtySixCard:0x007faf33ed4a10 @rank=:jack, @suit=:spades>, #<SixtySixCard:0x007faf33ed4b78 @rank=9, @suit=:spades>, #<SixtySixCard:0x007faf33ecbb18 @rank=:ace, @suit=:hearts>, #<SixtySixCard:0x007faf33ecbe88 @rank=10, @suit=:hearts>, #<SixtySixCard:0x007faf33ed6fb8 @rank=:king, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4100 @rank=:queen, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4218 @rank=:jack, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4330 @rank=9, @suit=:hearts>, #<SixtySixCard:0x007faf33ec97f0 @rank=:ace, @suit=:diamonds>, #<SixtySixCard:0x007faf33ec9d90 @rank=10, @suit=:diamonds>, #<SixtySixCard:0x007faf33eca768 @rank=:king, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecab50 @rank=:queen, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecb230 @rank=:jack, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecb460 @rank=9, @suit=:diamonds>, #<SixtySixCard:0x007faf33ec84b8 @rank=:ace, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8648 @rank=10, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8940 @rank=:king, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8b70 @rank=:queen, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8da0 @rank=:jack, @suit=:clubs>, #<SixtySixCard:0x007faf33ec9188 @rank=9, @suit=:clubs>]
       the missing elements were:      [#<Card:0x007faf33eb6b28 @rank=:ace, @suit=:spades>, #<Card:0x007faf33eb6c40 @rank=:king, @suit=:spades>, #<Card:0x007faf33eb6ce0 @rank=:queen, @suit=:spades>, #<Card:0x007faf33eb6d80 @rank=:jack, @suit=:spades>, #<Card:0x007faf33eb6b78 @rank=10, @suit=:spades>, #<Card:0x007faf33eb6ee8 @rank=9, @suit=:spades>, #<Card:0x007faf33eb6fb0 @rank=:ace, @suit=:hearts>, #<Card:0x007faf33eb70f0 @rank=:king, @suit=:hearts>, #<Card:0x007faf33eb7190 @rank=:queen, @suit=:hearts>, #<Card:0x007faf33eb7230 @rank=:jack, @suit=:hearts>, #<Card:0x007faf33eb7050 @rank=10, @suit=:hearts>, #<Card:0x007faf33eb7370 @rank=9, @suit=:hearts>, #<Card:0x007faf33eb7410 @rank=:ace, @suit=:diamonds>, #<Card:0x007faf33eb7578 @rank=:king, @suit=:diamonds>, #<Card:0x007faf33eb7618 @rank=:queen, @suit=:diamonds>, #<Card:0x007faf33eb7668 @rank=:jack, @suit=:diamonds>, #<Card:0x007faf33eb7488 @rank=10, @suit=:diamonds>, #<Card:0x007faf33eb77d0 @rank=9, @suit=:diamonds>, #<Card:0x007faf33eb7820 @rank=:ace, @suit=:clubs>, #<Card:0x007faf33eb7960 @rank=:king, @suit=:clubs>, #<Card:0x007faf33eb79d8 @rank=:queen, @suit=:clubs>, #<Card:0x007faf33eb7a78 @rank=:jack, @suit=:clubs>, #<Card:0x007faf33eb78e8 @rank=10, @suit=:clubs>, #<Card:0x007faf33eb7b40 @rank=9, @suit=:clubs>]
       the extra elements were:        [#<SixtySixCard:0x007faf33ed44e8 @rank=:ace, @suit=:spades>, #<SixtySixCard:0x007faf33ed46a0 @rank=10, @suit=:spades>, #<SixtySixCard:0x007faf33ed47e0 @rank=:king, @suit=:spades>, #<SixtySixCard:0x007faf33ed48f8 @rank=:queen, @suit=:spades>, #<SixtySixCard:0x007faf33ed4a10 @rank=:jack, @suit=:spades>, #<SixtySixCard:0x007faf33ed4b78 @rank=9, @suit=:spades>, #<SixtySixCard:0x007faf33ecbb18 @rank=:ace, @suit=:hearts>, #<SixtySixCard:0x007faf33ecbe88 @rank=10, @suit=:hearts>, #<SixtySixCard:0x007faf33ed6fb8 @rank=:king, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4100 @rank=:queen, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4218 @rank=:jack, @suit=:hearts>, #<SixtySixCard:0x007faf33ed4330 @rank=9, @suit=:hearts>, #<SixtySixCard:0x007faf33ec97f0 @rank=:ace, @suit=:diamonds>, #<SixtySixCard:0x007faf33ec9d90 @rank=10, @suit=:diamonds>, #<SixtySixCard:0x007faf33eca768 @rank=:king, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecab50 @rank=:queen, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecb230 @rank=:jack, @suit=:diamonds>, #<SixtySixCard:0x007faf33ecb460 @rank=9, @suit=:diamonds>, #<SixtySixCard:0x007faf33ec84b8 @rank=:ace, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8648 @rank=10, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8940 @rank=:king, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8b70 @rank=:queen, @suit=:clubs>, #<SixtySixCard:0x007faf33ec8da0 @rank=:jack, @suit=:clubs>, #<SixtySixCard:0x007faf33ec9188 @rank=9, @suit=:clubs>]
     Shared Example Group: "a deck" called from /tmp/d20151112-27349-5h228p/spec.rb:400
     # /tmp/d20151112-27349-5h228p/spec.rb:18:in `block (2 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  9) SixtySixDeck hand #twenty? returns true for king and queen not of the trump suit
     Failure/Error: expect(hand.twenty?(:hearts)).to be true
       
       expected #<TrueClass:20> => true
            got #<FalseClass:0> => false
       
       Compared using equal?, which compares object identity,
       but expected and actual are not the same object. Use
       `expect(actual).to eq(expected)` if you don't care about
       object identity in this example.
     # /tmp/d20151112-27349-5h228p/spec.rb:439:in `block (4 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/language/ruby/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

Finished in 0.04836 seconds
57 examples, 9 failures

Failed examples:

rspec /tmp/d20151112-27349-5h228p/spec.rb:14 # BeloteDeck behaves like a deck fills the deck if no initialize parameters are given
rspec /tmp/d20151112-27349-5h228p/spec.rb:220 # BeloteDeck hand #highest_of_suit returns the strongest card of the specified suit
rspec /tmp/d20151112-27349-5h228p/spec.rb:239 # BeloteDeck hand #belote? returns true if there is a king and a queen of the same suit
rspec /tmp/d20151112-27349-5h228p/spec.rb:272 # BeloteDeck hand #tierce? with tierce returns true for cards with names
rspec /tmp/d20151112-27349-5h228p/spec.rb:74 # BeloteDeck hand #carre_of_jacks? behaves like carre-checking method returns true when there is a carre
rspec /tmp/d20151112-27349-5h228p/spec.rb:74 # BeloteDeck hand #carre_of_nines? behaves like carre-checking method returns true when there is a carre
rspec /tmp/d20151112-27349-5h228p/spec.rb:74 # BeloteDeck hand #carre_of_aces? behaves like carre-checking method returns true when there is a carre
rspec /tmp/d20151112-27349-5h228p/spec.rb:14 # SixtySixDeck behaves like a deck fills the deck if no initialize parameters are given
rspec /tmp/d20151112-27349-5h228p/spec.rb:429 # SixtySixDeck hand #twenty? returns true for king and queen not of the trump suit

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

Адриана обнови решението на 10.11.2015 23:27 (преди над 8 години)

+module SuitsConstant
+ SUITS = [:spades, :hearts, :diamonds, :clubs]
+end
+
+module WarConstants
+ include SuitsConstant
+ RANKS = [2, 3, 4, 5, 6, 7, 8, 9, 10, :jack, :queen, :king, :ace]
+end
+
+module BeloteConstants
+ include SuitsConstant
+ RANKS = [7, 8, 9, :jack, :queen, :king, 10, :ace]
+end
+
+module SixtySixConstants
+ include SuitsConstant
+ RANKS = [9, :jack, :queen, :king, 10, :ace]
+end
+
+class Card
+ include WarConstants
+
+ attr_reader :rank
+ attr_reader :suit
+
+ def initialize(rank, suit)
+ initialize_card(RANKS, rank, suit)
+ end
+
+ def to_s
+ capitalize_first_letter(rank) << " of " << capitalize_first_letter(suit)
+ end
+
+ def ==(another)
+ self.class == another.class && self.rank == another.rank &&
+ self.suit == another.suit
+ end
+
+ def <=>(another)
+ compare(another, RANKS)
+ end
+
+ private
+
+ def initialize_card(ranks, rank, suit)
+ if ranks.include?(rank) && SUITS.include?(suit)
+ @rank, @suit = rank, suit
+ else
+ raise "Invalid card"
+ end
+ end
+
+ def capitalize_first_letter(word)
+ word.to_s.split.map(&:capitalize).join(' ')
+ end
+
+ def compare(another, ranks)
+ if ranks.find_index(self.rank) < ranks.find_index(another.rank)
+ compare_smaller_rank(self.suit, another.suit)
+ elsif ranks.find_index(self.rank) > ranks.find_index(another.rank)
+ compare_larger_rank(self.suit, another.suit)
+ else
+ compare_equal_rank(self.suit, another.suit)
+ end
+ end
+
+ def compare_smaller_rank(self_suit, another_suit)
+ if SUITS.find_index(self_suit) >= SUITS.find_index(another_suit)
+ 1
+ elsif SUITS.find_index(self_suit) < SUITS.find_index(another_suit)
+ -1
+ end
+ end
+
+ def compare_larger_rank(self_suit, another_suit)
+ if SUITS.find_index(self_suit) <= SUITS.find_index(another_suit)
+ -1
+ elsif SUITS.find_index(self_suit) > SUITS.find_index(another_suit)
+ 1
+ end
+ end
+
+ def compare_equal_rank(self_suit, another_suit)
+ if SUITS.find_index(self_suit) < SUITS.find_index(another_suit)
+ -1
+ elsif SUITS.find_index(self_suit) > SUITS.find_index(another_suit)
+ 1
+ else
+ 0
+ end
+ end
+
+end
+
+class BeloteCard < Card
+ include BeloteConstants
+
+ def initialize(rank, suit)
+ initialize_card(RANKS, rank, suit)
+ end
+
+ def <=>(another)
+ compare(another, RANKS)
+ end
+end
+
+class SixtySixCard < Card
+ include SixtySixConstants
+
+ def initialize(rank, suit)
+ initialize_card(RANKS, rank, suit)
+ end
+
+ def <=>(another)
+ compare(another, RANKS)
+ end
+end
+
+class Hand
+ attr_accessor :hand
+
+ def initialize(cards)
+ @hand = cards
+ end
+
+ def allow_face_up?
+ @hand.size <= 3
+ end
+
+ def play_card
+ @hand.pop
+ end
+
+ def size
+ @hand.size
+ end
+
+ def to_s
+ @hand.to_s
+ end
+end
+
+class BeloteHand < Hand
+ include BeloteConstants
+
+ def highest_of_suit(suit)
+ max = @hand.first
+ @hand.select{|card|
+ card.suit == suit
+ }.each{|card_of_suit|
+ if RANKS.find_index(max.rank) < RANKS.find_index(card_of_suit.rank)
+ max = card_of_suit
+ end
+ }
+ max
+ end
+
+ def belote?
+ @hand.group_by{|card| card.suit}.
+ each{|all_of_suit|
+ all_of_suit.shift
+ if (all_of_suit.include?(:king) && all_of_suit.include?(:queen))
+ return true
+ end
+ }
+ false
+ end
+
+ def tierce?
+ consequential?(3)
+ end
+
+ def quarte?
+ consequential?(4)
+ end
+
+ def quint?
+ consequential?(5)
+ end
+
+ def carre_of_jacks?
+ carre?(:jack)
+ end
+
+ def carre_of_nines?
+ carre?(9)
+ end
+
+ def carre_of_aces?
+ carre?(:ace)
+ end
+
+ private
+
+ def consequential?(number)
+ suits = @hand.group_by{ |card_in_hand|
+ card_in_hand.suit
+ }
+ suits.each { |all_of_suit|
+ all_of_suit.shift
+ if loop_all_of_suit(number, all_of_suit)
+ return true
+ end
+ }
+ false
+ end
+
+ def loop_all_of_suit(number, all_of_suit)
+ all_of_suit.each{ |set|
+ set.sort
+ if find_match(number, set)
+ return true
+ end
+ }
+ false
+ end
+
+ def find_match(number, set)
+ set.each_cons(number){|sorted_set|
+ if has_match(number, sorted_set)
+ return true
+ end
+ }
+ false
+ end
+
+ def has_match(number, sorted_set)
+ RANKS.each_cons(number){|ranks|
+ if ((ranks & sorted_set.map{|card| card.rank}).size == 3)
+ return true
+ end
+ }
+ false
+ end
+
+ def carre?(rank)
+ [BeloteCard.new(rank, :spades), BeloteCard.new(rank, :diamonds),
+ BeloteCard.new(rank, :hearts), BeloteCard.new(rank, :clubs)].all?{|rank|
+ @hand.include?(rank)
+ }
+ end
+
+end
+
+class SixtySixHand < Hand
+ include SixtySixConstants
+
+ def twenty?(trump_suit)
+ SUITS.each{|suit|
+ if(suit != trump_suit && @hand.include?(SixtySixCard.new(:queen, suit)) &&
+ @hand.include?(SixtySixCard.new(:king, suit)))
+ return true
+ end
+ }
+ false
+ end
+
+ def forty?(trump_suit)
+ @hand.include?(SixtySixCard.new(:queen, trump_suit)) &&
+ @hand.include?(SixtySixCard.new(:king, trump_suit))
+ end
+
+end
+
+class Deck
+ include Enumerable
+ include SuitsConstant
+
+ attr_reader :size
+ attr_accessor :cards
+
+ def initialize(cards = [])
+ @cards = cards
+ end
+
+ def iterate(suits, ranks, *game)
+ if @cards == []
+ each_suit(suits, ranks, *game){ |card| yield card}
+ else
+ @cards.each{ |card|
+ yield card
+ }
+ end
+ end
+
+ def draw_top_card
+ @cards.shift
+ end
+
+ def draw_bottom_card
+ @cards.pop
+ end
+
+ def top_card
+ @cards.first
+ end
+
+ def bottom_card
+ @cards.last
+ end
+
+ def shuffle
+ @cards.shuffle!
+ end
+
+ def sort
+ @cards.sort!
+ end
+
+ def to_s
+ result = ""
+ @cards.each{|card|
+ result << card.to_s << "\n"
+ }
+ result
+ end
+
+ def size
+ @cards.size
+ end
+
+ private
+
+ def each_suit(suits, ranks, *game)
+ suits.each{ |suit|
+ each_rank(ranks, suit, *game){ |card| yield card}
+ }
+ end
+
+ def each_rank(ranks, suit, *game)
+ ranks.each { |rank|
+ card = instantiate_card(rank, suit, *game)
+ @cards << card
+ yield card
+ }
+ end
+
+ def instantiate_card(rank, suit, *game)
+ if game == [:belote]
+ BeloteCard.new(rank, suit)
+ elsif game == [:sixty_six]
+ SixtySixCard.new(rank, suit)
+ else
+ Card.new(rank, suit)
+ end
+ end
+
+end
+
+class WarDeck < Deck
+ include WarConstants
+
+ def initialize(cards = [])
+ super
+ self.each{ |card| }
+ end
+
+ def each(&block)
+ iterate(SUITS, RANKS){ |card| yield card }
+ end
+
+ def deal
+ Hand.new(@cards.shift(26))
+ end
+
+end
+
+class BeloteDeck < Deck
+ include BeloteConstants
+
+ def initialize(cards = [])
+ super
+ self.each{ |card| }
+ end
+
+ def each(&block)
+ iterate(SUITS, RANKS, :belote){ |card| yield card }
+ end
+
+ def deal
+ BeloteHand.new(@cards.shift(8))
+ end
+
+end
+
+class SixtySixDeck < Deck
+ include SixtySixConstants
+
+ def initialize(cards = [])
+ super
+ self.each{ |card| }
+ end
+
+ def each(&block)
+ iterate(SUITS, RANKS, :sixty_six){ |card| yield card }
+ end
+
+ def deal
+ SixtySixHand.new(@cards.shift(6))
+ end
+
+end

Имаш проблеми със спазването на конвенциите на места, направи справка с ръководството за стил. Не ползвай { ... } за многоредови блокове. Тук-таме подредбата на кода ти е странна и нестандартна.

Прегледай решенията на колеги и нашето примерно решение за алтернативни идеи.