Flotador de redondeo en rubí


150

Tengo problemas para redondear. Tengo un flotador, que quiero redondear a la centésima de un decimal. Sin embargo, solo puedo usar lo .roundque básicamente lo convierte en un int, lo que significa que 2.34.round # => 2. hay una manera simple de hacer algo como2.3465 # => 2.35

Respuestas:


181

Al mostrar, puede usar (por ejemplo)

>> '%.2f' % 2.3465
=> "2.35"

Si desea almacenarlo redondeado, puede usar

>> (2.3465*100).round / 100.0
=> 2.35

2
Gracias. No me di cuenta de que Sprintf se encargaría de redondear por mí. sprintf '%.2f', 2.3465También funciona.
Noah Sussman

66
value.round (2) es mejor que esta solución
Kit Ho

12
Tenga en cuenta que 2.3000.round(2) => 2.3y sprintf '%.2f', 2.300 => 2.30. En mi opinión, esta es una falla en round (), o debería tener una opción para preservar los ceros finales.
Excalibur

14
@Excalibur 2.3000.round(2)es un número, no una cadena. No hay forma de que el número 2.3sea ​​diferente 2.30, por lo que no hay forma de tener una opción para preservar los ceros finales. Podrías hacer tu propia clase de números_con_significancia pero entonces ya tenemos cadenas.
Roobie Nuby

66
Tenga en cuenta que aunque esto hace el trabajo de dos cifras decimales, hay un defecto en '%.3f' % 1.2345(3 lugares decimales, no 2), sin embargo !! Lo mismo para sprintftambién. Tener cuidado. Eso va a volver => 1.234 , no => 1.235 como la mayoría esperaría (OIA, después de que el segundo decimal, rondas sprintf 5 hacia abajo y sólo un 6 rondas arriba). Es por eso que el comentario anterior de Kit Ho tiene más de 25 votos a favor. Es más seguro de usar, '%.3f' % 1.2345.round(3)por lo que el número se redondea correctamente .roundprimero, luego se formatea (con ceros finales, si es necesario).
likethesky

392

Pase un argumento a redondear que contenga el número de decimales a redondear

>> 2.3465.round
=> 2
>> 2.3465.round(2)
=> 2.35
>> 2.3465.round(3)
=> 2.347

8
Esto parecería más sensato que multiplicar, redondear y dividir. +1
Mark Embling

3
Hmm, este método no parece estar en ruby ​​1.8.7. Tal vez en 1.9?
Brian Armstrong

2
@Brian. Esto definitivamente está en 1.9 y también está en rieles (con lo que esta pregunta fue etiquetada)
Steve Weet

3
El método de redondeo de Ruby 1.8.7 no tiene esta habilidad, agregar el parámetro de redondeo de lugar decimal es una habilidad 1.9
bobmagoo

1
Tenga en cuenta que no obtiene ceros finales con esto, por lo que 1.1.round(2)=> 1.1no1.10
NotAnAmbiTurner

9

puede usar esto para redondear a una precisión.

//to_f is for float

salary= 2921.9121
puts salary.to_f.round(2) // to 2 decimal place                   

puts salary.to_f.round() // to 3 decimal place          

7

Puede agregar un método en Float Class, lo aprendí de stackoverflow:

class Float
    def precision(p)
        # Make sure the precision level is actually an integer and > 0
        raise ArgumentError, "#{p} is an invalid precision level. Valid ranges are integers > 0." unless p.class == Fixnum or p < 0
        # Special case for 0 precision so it returns a Fixnum and thus doesn't have a trailing .0
        return self.round if p == 0
        # Standard case  
        return (self * 10**p).round.to_f / 10**p
    end
end

3

También puede proporcionar un número negativo como argumento del roundmétodo para redondear al múltiplo más cercano de 10, 100 y así sucesivamente.

# Round to the nearest multiple of 10. 
12.3453.round(-1)       # Output: 10

# Round to the nearest multiple of 100. 
124.3453.round(-2)      # Output: 100

2
def rounding(float,precision)
    return ((float * 10**precision).round.to_f) / (10**precision)
end


1

Si solo necesita mostrarlo, usaría el ayudante number_with_precision . Si lo necesita en otro lugar, usaría, como señaló Steve Weet, el roundmétodo


1
Tenga en cuenta que number_with_precisiones un método exclusivo de Rails.
Smar

0

Para ruby ​​1.8.7 puede agregar lo siguiente a su código:

class Float
    alias oldround:round
    def round(precision = nil)
        if precision.nil?
            return self
        else
            return ((self * 10**precision).oldround.to_f) / (10**precision)
        end 
    end 
end
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.