我想用Ruby开发基于卡片的游戏,我想以 TDD 的方式进行游戏。
我想写的第一堂课是 Player 。 每位玩家拥有13张牌的牌,并且在他/她的回合中可以选择并玩1张牌来传递。
我还没有开发过任何其他类(比如card,hand,..),我想知道如何测试这个依赖于其他类的主题?
我知道Mocks但我不知道如何使用它们。
例如,在这种情况下,我们知道当玩家玩时,一张卡片必须从他/她的手中取出。
这是我的代码:
require "rspec"
require "lib/player"
describe Player do
before(:each) do
hand=mock("Hand")
hand.should_receive(:count).and_return(13)
subject.hand=hand
end
it "should choose and play a card from her/his hand" do
subject.hand.count.should==13
card_selected=subject.play(2) # card #2 in his/her hand
subject.hand.count.should=12
end
end
另外,在实现中我们依赖于Hand类,我该如何处理它?</ p>
答案 0 :(得分:2)
我已经看到了我的嘲讽和抄袭,我已经看到了大量的测试套件通过,即使应用程序被打破了,因为一半的代码甚至不再存在。
我得出的结论是,应该非常谨慎地使用剔除和嘲弄。那个,以及它应该尽可能晚地介绍的事实。
这是嘲笑为时尚早的案例之一。你只是因为你还没有上课Hand
而嘲笑。
作为旁注,测试本身需要改进。仔细看看这些内容:
hand.should_receive(:count).and_return(13)
subject.hand=hand
subject.hand.count.should==13
subject.hand.count.should=12
当然,subject.hand.count.should==13
通过,你只是将它存根到这个值。当然,subject.hand.count.should=12
通过,因为您没有致电==
。如果你把它改成了真正的期望,你会想知道为什么它会失败。它失败了,因为您将Hand#count
存根到总是返回13。
你在这里做的是模拟被测API的一部分。不要这样做。相反,从婴儿步骤开始。这可能意味着:
你从内心开始,逐步解决问题。所以从这个案例中最内层的类Hand
开始。一旦你到达Player
,所有的部分都会很好地融合在一起而不会嘲笑。
您从Player
开始,直到您绝对需要其他类(如果“有意义的API”的参数吸引您,请执行此操作)。这意味着:在NameError
上等待Hand
。然后根据需要实现尽可能多的Hand
类。然后返回Player
另外,查看你的代码提出了一个问题:出于好奇,你为什么要首先将玩家和她的手分开?