Como arredondar para uma casa decimal em Javascript?

378

Você pode arredondar um número em javascript para 1 caractere após o ponto decimal (corretamente arredondado)?

Eu tentei o * 10, round, / 10, mas deixa duas casas decimais no final do int.

andador
fonte
9
Math.round(n * 10) / 10funciona. Qual é o seu código?
Ben Fleming

Respostas:

729

Math.round(num * 10) / 10 funciona, aqui está um exemplo ...

var number = 12.3456789
var rounded = Math.round(number * 10) / 10
// rounded is 12.3

se você quiser que ele tenha uma casa decimal, mesmo quando isso seria um 0, adicione ...

var fixed = rounded.toFixed(1)
// fixed is always to 1 d.p.
// NOTE: .toFixed() returns a string!

// To convert back to number format
parseFloat(number.toFixed(2))
// 12.34
// but that will not retain any trailing zeros

// So, just make sure it is the last step before output,
// and use a number format during calculations!

EDIT: Adicionar rodada com função de precisão ...

Usando este princípio, para referência, aqui está uma pequena função redonda prática que exige precisão ...

function round(value, precision) {
    var multiplier = Math.pow(10, precision || 0);
    return Math.round(value * multiplier) / multiplier;
}

... uso ...

round(12345.6789, 2) // 12345.68
round(12345.6789, 1) // 12345.7

... o padrão é arredondar para o número inteiro mais próximo (precisão 0) ...

round(12345.6789) // 12346

... e pode ser usado para arredondar para o valor mais próximo de 10 ou 100 etc ...

round(12345.6789, -1) // 12350
round(12345.6789, -2) // 12300

... e manuseio correto de números negativos ...

round(-123.45, 1) // -123.4
round(123.45, 1) // 123.5

... e pode ser combinado com o toFixed para formatar consistentemente como string ...

round(456.7, 2).toFixed(2) // "456.70"
Billy Moon
fonte
45
Cuidado ao usar, .toFixed()pois ele retorna uma string quando você quiser um número.
14/12
11
Legal, obviamente, o uso parseFloatremoverá os decimais deixados por .toFixed()se for um número inteiro (zeros). Geralmente, se você quiser fazer as contas, é melhor seguir o seu primeiro exemplo. Se você deseja exibir um número na sua interface do usuário, use .toFixed().
C13
Hmmm ... isso faz sentido, de qualquer maneira que você converta em número, deve sempre retirar os zeros errados, e é por isso que ele precisa permanecer um fio. Eu acho que deve sempre ser o último passo antes da exibição, e não usado nos cálculos.
Billy Lua
2
Tenha cuidado ao usar .toFixed(), pois pode retornar diferentes resultados de arredondamento para diferentes navegadores. Leia este post para obter detalhes sobre o tópico!
Wilt
11
Posso adicionar um zero se nenhum DP estiver presente?
Nick
102
var number = 123.456;

console.log(number.toFixed(1)); // should round to 123.5
Pablo Fernandez
fonte
4
Às vezes toFixed()tem falhas - eu a vi em um navegador Chrome onde chamo toFixed(), em seguida, converto em uma string e mostra algo como 10.00000000068- estranho. Não é possível reproduzir isso de forma confiável.
Hamish Grubijan
Sim, constatei falhas com toFixed (), mesmo com apenas algumas casas decimais. Arredondou a fração 4 para o próximo número mais alto, em vez de mais baixo, se bem me lembro.
Dalibor
11
como mencionado por @cobby acima: ter cuidado usando .toFixed()como ele retorna um Stringquando você talvez quer umNumber
Ricardo
28

Se você usar Math.round(5.01), receberá em 5vez de 5.0.

Se você usar, toFixedterá problemas de arredondamento .

Se você quer o melhor dos dois mundos, combine os dois:

(Math.round(5.01 * 10) / 10).toFixed(1)

Você pode criar uma função para isso:

function roundedToFixed(_float, _digits){
  var rounded = Math.pow(10, _digits);
  return (Math.round(_float * rounded) / rounded).toFixed(_digits);
}
Jasper de Vries
fonte
Por que os sublinhados dos parâmetros, por exemplo (_float, _digits)? Sinta-se livre para postar um link onde eu possa encontrar a resposta por mim mesmo. Obrigado
Shark Lasers
23

lodashtem um roundmétodo:

_.round(4.006);
// => 4

_.round(4.006, 2);
// => 4.01

_.round(4060, -2);
// => 4100

Docs .

Fonte .

Kevin Leary
fonte
11

Eu voto a favor toFixed(), mas, para o registro, aqui está outra maneira que usa deslocamento de bits para converter o número em um int. Portanto, sempre arredonda para zero (baixo para números positivos, alto para negativos).

var rounded = ((num * 10) << 0) * 0.1;

Mas ei, como não há chamadas de função, é muito rápido. :)

E aqui está um que usa correspondência de string:

var rounded = (num + '').replace(/(^.*?\d+)(\.\d)?.*/, '$1$2');

Eu não recomendo usar a variante de string, apenas dizendo.

jimbo
fonte
7

Tente com isto:

var original=28.453

// 1.- round "original" to two decimals
var result = Math.round (original * 100) / 100  //returns 28.45

// 2.- round "original" to 1 decimal
var result = Math.round (original * 10) / 10  //returns 28.5

// 3.- round 8.111111 to 3 decimals
var result = Math.round (8.111111 * 1000) / 1000  //returns 8.111

menos complicado e mais fácil de implementar ...

com isso, você pode criar uma função para fazer:

function RoundAndFix (n, d) {
    var m = Math.pow (10, d);
    return Math.round (n * m) / m;
}

EDIT : veja como arredondar usando ROUND MEIA CIMA. Modo de arredondamento que muitos de nós aprendemos na escola primária

atiruz
fonte
Não: RoundAndFix (1.005, 2).
Noyo
4

x = número, n = casas decimais:

function round(x, n) {
    return Math.round(x * Math.pow(10, n)) / Math.pow(10, n)
}
super
fonte
Não: redondo (1.005, 2).
Noyo
4

Por que não apenas

let myNumber = 213.27321;
+myNumber.toFixed(1); // => 213.3
  1. toFixed : retorna uma string que representa o número fornecido usando a notação de ponto fixo.
  2. Unário mais (+) : o operador unário mais precede seu operando e avalia seu operando, mas tenta convertê-lo em um número, se já não estiver.
goulashsoup
fonte
3
var num = 34.7654;

num = Math.round(num * 10) / 10;

console.log(num); // Logs: 34.8
Joseph Silber
fonte
3

Para concluir a melhor resposta:

var round = function ( number, precision )
{
    precision = precision || 0;
    return parseFloat( parseFloat( number ).toFixed( precision ) );
}

O número do parâmetro de entrada "nem" pode sempre ser um número; nesse caso, .toFixed não existe.

Klodoma
fonte
3

Versão ES 6 da resposta aceita:

function round(value, precision) {
    const multiplier = 10 ** (precision || 0);
    return Math.round(value * multiplier) / multiplier;
}
Koustav Ray
fonte
3

Usando o método toPrecision:

var a = 1.2345
a.toPrecision(2)

// result "1.2"
EZ
fonte
De longe a melhor resposta que eu tentei. Obrigado.
Ste
Mas você tem que ter cuidado porque 12.345.toPrecision( 2 )é "12".
Joshua Pinter
2

Se seu método não funcionar, plz publique seu código.

No entanto, você pode realizar a tarefa de arredondamento como:

var value = Math.round(234.567*100)/100

Vai lhe dar 234,56

similarmente

 var value = Math.round(234.567*10)/10

Vai dar 234,5

Dessa forma, você pode usar uma variável no lugar da constante, conforme usado acima.

jagbandhuster
fonte
1

Pouco filtro angular, se alguém quiser:

angular.module('filters').filter('decimalPlace', function() {
    return function(num, precision) {
        var multiplier = Math.pow(10, precision || 0);
        return Math.round(num * multiplier) / multiplier;
    };
});

use se via:

{{model.value| decimalPlace}}
{{model.value| decimalPlace:1}}
{{model.value| decimalPlace:2}}

:)

sidonaldson
fonte
1

Em geral, o arredondamento é feito pela escala: round(num / p) * p

O uso da notação exponencial manipula o arredondamento dos números + ve, corretamente. No entanto, esse método falha ao arredondar os casos de borda corretamente.

function round(num, precision = 2) {
	var scaled = Math.round(num + "e" + precision);
	return Number(scaled + "e" + -precision);
}

// testing some edge cases
console.log( round(1.005, 2) );  // 1.01 correct
console.log( round(2.175, 2) );  // 2.18 correct
console.log( round(5.015, 2) );  // 5.02 correct

console.log( round(-1.005, 2) );  // -1    wrong
console.log( round(-2.175, 2) );  // -2.17 wrong
console.log( round(-5.015, 2) );  // -5.01 wrong

Aqui também está uma função que escrevi para fazer o arredondamento aritmético. Você pode testá-lo você mesmo.

/**
 * MidpointRounding away from zero ('arithmetic' rounding)
 * Uses a half-epsilon for correction. (This offsets IEEE-754
 * half-to-even rounding that was applied at the edge cases).
 */

function RoundCorrect(num, precision = 2) {
	// half epsilon to correct edge cases.
	var c = 0.5 * Number.EPSILON * num;
//	var p = Math.pow(10, precision); //slow
	var p = 1; while (precision--> 0) p *= 10;
	if (num < 0)
		p *= -1;
	return Math.round((num + c) * p) / p;
}

// testing some edge cases
console.log(RoundCorrect(1.005, 2));  // 1.01 correct
console.log(RoundCorrect(2.175, 2));  // 2.18 correct
console.log(RoundCorrect(5.015, 2));  // 5.02 correct

console.log(RoundCorrect(-1.005, 2));  // -1.01 correct
console.log(RoundCorrect(-2.175, 2));  // -2.18 correct
console.log(RoundCorrect(-5.015, 2));  // -5.02 correct

Amr Ali
fonte
0

Isso parece funcionar de maneira confiável em qualquer coisa que eu jogue:

function round(val, multiplesOf) {
  var s = 1 / multiplesOf;
  var res = Math.ceil(val*s)/s;
  res = res < val ? res + multiplesOf: res;
  var afterZero = multiplesOf.toString().split(".")[1];
  return parseFloat(res.toFixed(afterZero ? afterZero.length : 0));
}

Ele é arredondado para que você precise modificá-lo de acordo com o caso de uso. Isso deve funcionar:

console.log(round(10.01, 1)); //outputs 11
console.log(round(10.01, 0.1)); //outputs 10.1
Ege Özcan
fonte
0

Se você se preocupa com o arredondamento adequado, então:

function roundNumericStrings(str , numOfDecPlacesRequired){ 
     var roundFactor = Math.pow(10, numOfDecPlacesRequired);  
     return (Math.round(parseFloat(str)*roundFactor)/roundFactor).toString();  }

Caso contrário, se não o fizer, você já terá uma resposta das postagens anteriores

str.slice(0, -1)
jsNovice
fonte
0

Math.round( num * 10) / 10 não funciona

Por exemplo, 1455581777.8-145558160.4dá-lhe 1310023617.3999999.

Então, use apenas num.toFixed(1)

PW
fonte
0

Fiz um que retorna o tipo de número e também coloca decimais apenas se necessário (sem preenchimento 0).

Exemplos:

roundWithMaxPrecision(11.234, 2); //11.23
roundWithMaxPrecision(11.234, 1); //11.2
roundWithMaxPrecision(11.234, 4); //11.23
roundWithMaxPrecision(11.234, -1); //10

roundWithMaxPrecision(4.2, 2); //4.2
roundWithMaxPrecision(4.88, 1); //4.9

O código:

function roundWithMaxPrecision (n, precision) {
    return Math.round(n * Math.pow(10, precision)) / Math.pow(10, precision);
}
Alberto
fonte
0

Eu encontrei uma maneira de evitar os problemas de precisão:

function badRound (num, precision) {
    const x = 10 ** precision;
    return Math.round(num * x) / x
}
// badRound(1.005, 2) --> 1

function round (num, precision) {
    const x = 10 ** (precision + 1);
    const y = 10 ** precision;
    return Math.round(Math.round(num * x) / 10) / y
}
// round(1.005, 2) --> 1.01
Lucas Montenegro
fonte
0
Math.round( mul/count * 10 ) / 10

Math.round(Math.sqrt(sqD/y) * 10 ) / 10

obrigado

Roy Neo
fonte