## 如何有效地清除Ruby的负零浮点数？内容来源于 Stack Overflow，并遵循CC BY-SA 3.0许可协议进行翻译与使用

• 回答 (2)
• 关注 (0)
• 查看 (28)

``````def clean_output(amount)
if amount.zero?
0.0
else
amount
end
end

``````

### 2 个回答

``````def clean_output(amount)
amount.zero? && 0.0 || amount
end
``````

``````irb(main):005:0> f = 0.0
=> 0.0
irb(main):006:0> f.zero? && 0.0 || f
=> 0.0
irb(main):007:0> f = -0.0
=> -0.0
irb(main):008:0> f.zero? && 0.0 || f
=> 0.0
irb(main):009:0> f=1.0
=> 1.0
irb(main):010:0> f.zero? && 0.0 || f
=> 1.0
``````

``````require 'benchmark'

def clean_output(amount)
if amount.zero?
0.0
else
amount
end
end

def clean_output2(amount)
amount.zero? && 0.0 || amount
end

def clean_output3(value)
value + 0
end

class Numeric
def clean_to_s
(nonzero? || abs).to_s
end
end

n = 5_000_000
Benchmark.bm(14) do |x|
x.report( "clean_output:"  ) { n.times { a = clean_output(-0.0)  } }
x.report( "clean_output2:" ) { n.times { a = clean_output2(-0.0) } }
x.report( "clean_output3:" ) { n.times { a = clean_output3(-0.0) } }
x.report( "clean_to_s:"    ) { n.times { a = 0.0.clean_to_s      } }
end
``````

``````ruby test.rb
user     system      total        real
clean_output:   2.120000   0.000000   2.120000 (  2.127556)
clean_output2:  2.230000   0.000000   2.230000 (  2.222796)
clean_output3:  2.530000   0.000000   2.530000 (  2.534189)
clean_to_s:     7.200000   0.010000   7.210000 (  7.200648)

ruby test.rb
user     system      total        real
clean_output:   2.120000   0.000000   2.120000 (  2.122890)
clean_output2:  2.200000   0.000000   2.200000 (  2.203456)
clean_output3:  2.540000   0.000000   2.540000 (  2.533085)
clean_to_s:     7.200000   0.010000   7.210000 (  7.204332)
``````

``````require 'benchmark'

def clean_output(amount)
if amount.zero?
0.0
else
amount
end
end

def clean_output2(amount)
amount.zero? && 0.0 || amount
end

def clean_output3(value)
value + 0
end

class Numeric
def clean_to_s
(nonzero? || abs).to_s
end

def clean_no_to_s
nonzero? || abs
end

end

n = 5_000_000
Benchmark.bm(14) do |x|
x.report( "clean_output:"  ) { n.times { a = clean_output(-0.0)  } }
x.report( "clean_output2:" ) { n.times { a = clean_output2(-0.0) } }
x.report( "clean_output3:" ) { n.times { a = clean_output3(-0.0) } }
x.report( "clean_to_s:"    ) { n.times { a = -0.0.clean_to_s     } }
x.report( "clean_no_to_s:" ) { n.times { a = -0.0.clean_no_to_s  } }
end
``````

``````ruby test.rb
user     system      total        real
clean_output:   3.030000   0.000000   3.030000 (  3.028541)
clean_output2:  2.990000   0.010000   3.000000 (  2.992095)
clean_output3:  3.610000   0.000000   3.610000 (  3.610988)
clean_to_s:     8.710000   0.010000   8.720000 (  8.718266)
clean_no_to_s:  5.170000   0.000000   5.170000 (  5.170987)

ruby test.rb
user     system      total        real
clean_output:   3.050000   0.000000   3.050000 (  3.050175)
clean_output2:  3.010000   0.010000   3.020000 (  3.004055)
clean_output3:  3.520000   0.000000   3.520000 (  3.525969)
clean_to_s:     8.710000   0.000000   8.710000 (  8.710635)
clean_no_to_s:  5.140000   0.010000   5.150000 (  5.142462)
``````

``````require 'benchmark'

n = 5_000_000
Benchmark.bm(9) do |x|
x.report( "nonzero?:" ) { n.times { -0.0.nonzero? } }
x.report( "abs:"      ) { n.times { -0.0.abs      } }
x.report( "to_s:"     ) { n.times { -0.0.to_s     } }
end
``````

``````ruby test.rb
user     system      total        real
nonzero?:  2.750000   0.000000   2.750000 (  2.754931)
abs:       2.570000   0.010000   2.580000 (  2.569420)
to_s:      4.690000   0.000000   4.690000 (  4.687808)

ruby test.rb
user     system      total        real
nonzero?:  2.770000   0.000000   2.770000 (  2.767523)
abs:       2.570000   0.010000   2.580000 (  2.569757)
to_s:      4.670000   0.000000   4.670000 (  4.678333)
``````

``````def clean_output(value)
value + 0
end
``````

``````> clean_output(3.0)
=> 3.0
> clean_output(-3.0)
=> -3.0
> clean_output(-0.0)
=> 0.0
``````