当我尝试在case语句中匹配字符串“3”时,如果范围上升到“9”,则匹配,但不匹配“10”。
我猜这和三重等于运算符有关,但我不知道它为什么在这个范围内,但不匹配。
下面是一个irb运行,记录了两种情况:有效(使用“9”)和无效(使用“10”):
case '3'
when ('0'...'9')
puts "number is valid"
else
puts "number is not valid"
end
输出: number is valid
```
case '3'
when ('0'...'10')
puts "number is valid"
else
puts "number is not valid"
end
输出: `number is not valid` 我用作预期结果参考的方法如下
Enumerable#include? `Enumerable#member?` 当转换为数组时,查看输出是什么是( `Enumerable#to_a` ).
“案例平等”的结果( `===` )接线员让我大吃一惊。
puts ('0'...'10').include?('3')
=> true
puts ('0'...'10').member?('3')
=> true
puts ('0'...'10') === '3'
=> false
puts ('0'...'10').to_a
=> ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"]
2条答案
按热度按时间inkz8wg91#
范围使用
cover?
大小写相等。所以这是比较'3' >= '0' && '3' < '10'
结果是false
因为'3' < '10' #=> false
. 字符串根据字符值进行比较。为了更好地理解,您可能希望将字符串视为字符数组:
要解决此问题,请将案例输入转换为整数并使用整数范围:
这是因为整数的比较不是基于字符代码,而是基于实际值。
3 >= 0 && 3 < 10
结果true
.或者,您可以明确地告诉何时使用
member?
(或include?
)方法,而不是传递范围,而是传递方法。ee7vknir2#
===
说它相当于cover?
,后者的文档说明所以,在你的情况下,我们
以及
<=
以及<
在字符串上使用字典顺序进行比较,因此比较为false。另一方面,我们必须做更多的挖掘来找出什么
member?
/include?
实际上是这样的(两者是等价的)。如果我们查看源代码,就会发现两者都调用了一个名为range_include_internal
对于行为不同于cover?
. 后者要求rb_str_include_range_p
它有更多的特殊情况,包括你的数字情况。