我试图创建一个基本测验,要求我按照从头到尾的顺序命名预定的单词列表。
我创建了一个要求单词的函数,然后接受我的输入。如果我的单词与要求的单词相同,那么该功能应该打印出来#34;干得好!"然后转到下一个单词。如果我的话不是正确的话,它应该打印出来#34;不!再试一次:"让我输入另一个词。
该功能要求我输入一个单词但是当我输入正确的单词时,它会继续打印"不是!再试一次:"并问我另一个字,好像我输入了错误的字。无论我输入什么内容,这个循环似乎都是无穷无尽的。
代码:
def answers
words = [
"Hello",
"My",
"Name",
"Is",
"Josh",
"And",
"I",
"Am",
"A",
"Total",
"Idiot"
]
print "1: "
answer0 = gets.to_s
while answer0 != words[0]
print "Nope. Try again: "
answer0 = gets.to_s
end
puts "Good job!"
print "2: "
answer1 = gets.to_s
while answer1 != words[1]
print "Nope. Try again: "
answer1 = gets.to_s
end
puts "Good job!"
print "3: "
answer2 = gets.to_s
while answer2 != words[2]
print "Nope. Try again: "
answer1 = gets.to_s
end
puts "Good job!"
end
puts "Try to name all the WORDS, in order. Go!"
answers
答案 0 :(得分:2)
answer0 = gets.chomp
返回带有尾部换行符的字符串。摆脱换行符
answer0 = gets.to_s
puts "comparing #{answer0.inspect} to #{words[0].inspect}"
while answer0 != words[0]
ProTip:当你陷入类似情况时(两个看似相同的数据不匹配或者其他东西),开始调试打印所有的东西。在你的情况下,我会从这样的事情开始:
.inspect
然后,您可以直观地分析调试输出,并查看字符串是否相等。 secret_hash
部分非常重要。
答案 1 :(得分:2)
Ruby最强大的学习和调试工具是REPL工具irb
。在那里,您可以尝试不同的方法,并一次尝试一行代码。
要注意的第一件事是gets
拉出通常在结尾处有换行符的字符串。你键入"你好"你得到"hello\n"
。减轻这种情况的常用方法是gets.chomp
。出于某种原因,您使用gets.to_s
这是一件非常奇怪的事情。
另一件事是gets
可以返回nil
,这意味着没有更多输入。你永远不会对此进行测试,事实上.to_s
调用阻止了这一点,所以如果有人在你做好准备之前终止他们的输入,你最终可能陷入困境。在许多系统上,^ D(CTRL + D)将执行此操作。
编程时你想要做的事情之一是查找类似代码的块并用函数替换它们或将它们包装在循环中,以便消除或最小化复制。你可以看到那些" print"块大致相同,通常相差一位数。如果你可以迭代一系列数字怎么办?
由于each_with_index
方法,这实际上非常简单。将它与case
语句结合起来,使你的三个可能结果清晰,将它包装在一个循环中,要求输入,这段代码会急剧缩小:
words.each_with_index do |word, i|
print "What's word #%d?" % (i + 1)
loop do
guess = gets
case guess && guess.chomp.downcase
when nil
puts "\nWell, okay then."
exit(0)
when word
puts "Good job!"
break
else
print "Nope, try again: "
end
end
end
三个结果是:正确猜测,输入结束和猜测错误。现在所有这些都应该正确处理。
此处违反的原则是Zero, One or Infinity Rule,具有固定数量的print
块。正确的实现不会假设有多少个单词,并且当您从数组中添加或删除元素时,它会相应地进行调整。