web-dev-qa-db-ja.com

切り上げずに浮動小数点数を切り捨てます

3桁に切り捨てたい浮動小数点数がありますが、切り上げたくありません。

たとえば、1.01555555555555551.015に変換します(1.016ではありません)。

Rubyでこれを行うにはどうすればよいですか?

25
agentbanks217

floatがあると仮定して、これを試してください。

(x * 1000).floor / 1000.0

結果:

1.015

オンラインで動作することを確認してください: ideone

23
Mark Byers

BigDecimalに変換して、その上でtruncateを呼び出すこともできます。

1.237.to_d.truncate(2).to_f # will return 1.23
24
Sid Krishnan

Ruby 2.4Float#truncate メソッドは、オプションの引数として10進数の数字を取ります。

1.0155555555555555.truncate(3)
# => 1.015
14
potashin

千を掛ける、床、千で割る、フロート除算を行うようにしてください。

(x * 1000).floor / 1000.0

または、Ruby 1.9.2で、以前のバージョンでは使用できなかったバージョンのラウンドを使用して、

(x - 0.0005).round(3)
7
Don Roby

sidの答えは問題ありませんが、最初の要件を満たしていないため、Anwarのテストに失敗します。 Rubyが数値を簡単に変換しないように、rawを開始する必要があります。rawが取得するときにrawを開始するには、プレーンな文字列を使用する必要があります。

> "59.99999999999999999999" .to_d.truncate(2)
 => #BigDecimal:55a38a23cd68、 '0.5999E2'、18(45)> 
> "59.99999999999999999999" .to_d。 truncate(2).to_s 
 => "59.99" 
> "59.99999999999999999999" .to_d.truncate(2).to_f 
 => 59.99 

私は今日この問題に自分で遭遇したので、今これを共有するだけです:)

2
botp

このソリューションは、@ SidKrishnanによる素晴らしいBigDecimalトリックに基づいていますが、精度の問題に悩まされることなく、より大きなフロートを処理することもできます。

# Truncate a floating-point value without rounding up.
#
#   trunc_float(1.999, 2)   # => 1.99
#   trunc_float(1.999, 0)   # => 1.0
#
# @param value [Float]
# @param precision [Integer]
# @return [Float]
def trunc_float(value, precision)
  BigDecimal(value.to_s).truncate(precision).to_f
end

#--------------------------------------- Test

describe ".trunc_float" do
  def call(*args)
    trunc_float(*args)
  end

  it "generally works" do
    [
      [[1, 0], 1.0],
      [[1.999, 4], 1.999],
      [[1.999, 3], 1.999],
      [[1.999, 2], 1.99],
      [[1.999, 1], 1.9],
      [[1.999, 0], 1.0],
      [[111111111.9999999, 3], 111111111.999],
      [[1508675846.650976, 6], 1508675846.650976],
    ].each do |input, expected|
      output = call(*input)
      expect([input, output]).to eq [input, expected]
    end
  end
end
0
Alex Fortuna

私はこれを行うためのより「計算的な」方法が答えの範囲内にないのを見ました。以下の方法の使用を検討できます。

これは、C/Java/Pythonなど)などの他のプログラミング言語でも機能します(ただし、キャスト構文は異なります)。

q = 1.0155555555555555
(q * 1000).to_i / 1000.0
=> 1.015
0
Dennis