class Float
def signif(signs)
Float("%.#{signs}g" % self)
end
end
> (39.07).signif(3) #=> 39.1
> (9.0712).signif(3) #=> 9.07
> (9.0071).signif(3) #=> 9.01
> (0.01523).signif(3) #=> 0.0152
> (0.00150).signif(3) #=> 0.0015
> (39.01233).signif(3) #=> 39.0
OR
> require 'bigdecimal'
> BigDecimal.new(39.07, 3).to_f #=> 39.1
> BigDecimal.new(9.0712, 3).to_f #=> 9.07
> BigDecimal.new(9.0071, 3).to_f #=> 9.01
> BigDecimal.new(0.01523, 3).to_f #=> 0.0152
> BigDecimal.new(0.00150, 3).to_f #=> 0.0015
> BigDecimal.new(39.01233, 3).to_f #=> 39.0
UPDATE:
As above solution is not supporting more than three significant figures before the decimal point. so I have taken significant dynamically, now you can pass any big numbers. no need to pass significant. As per Cary Swoveland's comment if the value is equal as Integer version, should return Integer value instead Float.
class Float
def dynamic_signif
f = Float("%.#{self.to_i.to_s.size}g" % self)
n = (f==f.to_i) ? f.to_i : f
end
end
> (11327.314).dynamic_signif #=> 11327
> (11327.84).dynamic_signif #=> 11328
NOTE: As this method belongs to Float
class, so it won't work for FixNum
, you may need to convert Fixnum to Float.