ChatGPT解决这个技术问题 Extra ChatGPT

为什么Ruby中的除法返回整数而不是十进制值?

例如:

9 / 5  #=> 1

但我预计 1.8。如何获得正确的十进制(非整数)结果?为什么它会返回 1

请注意,如果您实际上是使用方法来返回此值,则无需将其分配给变量;只需 def method; a - b/8; end 将返回方法的计算结果,因为方法调用中的最后一个表达式是返回值。

A
Andrew Marshall

它正在做整数除法。您可以使用 to_f 强制进入浮点模式:

9.to_f / 5  #=> 1.8
9 / 5.to_f  #=> 1.8

如果您的值是变量而不是文字,这也适用。将一个值转换为浮点数足以将整个表达式强制转换为浮点运算。


这是比接受的答案更多的“rails”答案。
@muistooshort:对不起,我无法复制它。我可能做错了什么。
@SeanRyan 为什么特别是 Rails 而不是 Ruby?我不明白为什么(Ruby on)Rails 开发人员会与一般的 Ruby 开发人员做这件特定的事情。也许我只是在挑剔语义,大多数人只是在这种情况下将(Ruby on)Rails 和 Ruby 视为同义词。
有没有办法确保某个块中的所有数学都在浮点数上执行(而不是浮点数,强制浮点数)而不必.to_f一切?
@stevec对不起,我不知道这样的事情。
A
Andrew Marshall

它正在做整数除法。您可以通过添加 .0 使其中一个数字成为 Float

9.0 / 5  #=> 1.8
9 / 5.0  #=> 1.8

这可行,但下面的 to_f 答案似乎更有用。 to_f 在 Ruby 中更惯用吗?
如果您将两个包含整数的变量相除,例如 a.to_f / b.to_f 的答案会更好。如果您实际上是在将两个硬编码的整数相除(这可能很奇怪),那么使用 9.0 / 5 就可以了。
添加小数会使它成为浮点数,当您进行除法时,它将整数转换为浮点数,以便结果是浮点数。整数除法产生整数答案。对整数使用 to_f 更为明确,而将小数 .0 添加到整数则更为隐含。我建议使用 to_f 来让阅读代码的人更加明确,尽管对其他人的意图可能仍然不清楚。
K
Konrad Reiche

您还可以使用 Numeric#fdiv 方法:

9.fdiv(5)  #=> 1.8

这是我测试过的最快的方法,获得更高性能的唯一方法是除以浮点数的操作数。为了学习语法,我在 Ruby 中构建了一个素数生成器,现在我正在对其进行优化以了解最有效的方法。 Here's the benchmark I put together: require 'base64';require 'zlib';puts Zlib.inflate(Base64.decode64("eJxlkMEOwiAQRO98hekFuGzxQEwPXvwR01ZqiYHqBk2Tln8XDlWgnDbM25nJonq9NaoD7ZTtR9PigxK09zM7AkgRHieXTYHOsBNf1nklM6B6TuhYpdp+rPgSdiCOi/d/kQ71QBOtAVFLEDly05+UYQ2H+MckL6z0zioDdJG1S9K1K4iQAW66DhnmiqRYKEJFXMByux+XuOJ2XdO60dKsjC7aBtyTL5O5hLk="))
一个问题,它会像我们使用“十进制”一样保持精度吗?
如果结果是整数,有没有办法获得整数。有点像 17/2 = 8.5 和 16/2 = 8?
R
Renaud

您可以使用 irb 进行检查:

$ irb
>> 2 / 3
=> 0
>> 2.to_f / 3
=> 0.666666666666667
>> 2 / 3.to_f
=> 0.666666666666667

R
Rok Kralj

您可以包含 ruby mathn 模块。

require 'mathn'

这样,您将能够正常进行除法。

1/2              #=> (1/2)
(1/2) ** 3       #=> (1/8)
1/3*3            #=> 1
Math.sin(1/2)    #=> 0.479425538604203

这样,您将获得精确的除法(类 Rational),直到您决定应用无法表示为有理数的运算,例如 Math.sin


自 ruby 2.2 起,mathn 模块已被弃用
A
Andrew Marshall

5 更改为 5.0。你得到整数除法。


u
ucpuzz

Fixnum#to_r 这里没有提到,它是从 ruby 1.9 开始引入的。它将 Fixnum 转换为有理形式。以下是其使用示例。只要使用的所有数字都是 Fixnum,这也可以给出精确的除法。

 a = 1.to_r  #=> (1/1) 
 a = 10.to_r #=> (10/1) 
 a = a / 3   #=> (10/3) 
 a = a * 3   #=> (10/1) 
 a.to_f      #=> 10.0

对有理数进行浮点运算的示例将结果转换为浮点数。

a = 5.to_r   #=> (5/1) 
a = a * 5.0  #=> 25.0