Question Arrondir à au plus 2 décimales (seulement si nécessaire)


Je voudrais arrondir au plus 2 décimales, mais seulement si nécessaire.

Contribution:

10
1.7777777
9.1

Sortie:

10
1.78
9.1

Comment puis-je faire cela dans JavaScript?


1835
2017-08-06 17:17


origine


Réponses:


Utilisation Math.round(num * 100) / 100


2280
2017-08-06 17:20



Si la valeur est un type de texte:

parseFloat("123.456").toFixed(2);

Si la valeur est un nombre:

var numb = 123.23454;
numb = numb.toFixed(2);

Il y a un inconvénient que des valeurs comme 1.5 donneront "1,50" comme sortie. Une solution proposée par @minitech:

var numb = 1.5;
numb = +numb.toFixed(2);
// Note the plus sign that drops any "extra" zeroes at the end.
// It changes the result (which is a string) into a number again (think "0 + foo"),
// which means that it uses only as many digits as necessary.

Il semble que Math.round est une meilleure solution. Mais ce n'est pas! Dans certains cas, il sera NE PAS rond correctement:

Math.round(1.005 * 1000)/1000 // Returns 1 instead of expected 1.01!

toFixed () sera également NE PAS rond correctement dans certains cas (testé dans Chrome v.55.0.2883.87)!

Exemples:

parseFloat("1.555").toFixed(2); // Returns 1.55 instead of 1.56.
parseFloat("1.5550").toFixed(2); // Returns 1.55 instead of 1.56.
// However, it will return correct result if you round 1.5551.
parseFloat("1.5551").toFixed(2); // Returns 1.56 as expected.

1.3555.toFixed(3) // Returns 1.355 instead of expected 1.356.
// However, it will return correct result if you round 1.35551.
1.35551.toFixed(2); // Returns 1.36 as expected.

Je suppose, c'est parce que 1.555 est en fait quelque chose comme float 1.55499994 dans les coulisses.

Solution 1 est d'utiliser un script avec l'algorithme d'arrondi requis, par exemple:

function roundNumber(num, scale) {
  if(!("" + num).includes("e")) {
    return +(Math.round(num + "e+" + scale)  + "e-" + scale);
  } else {
    var arr = ("" + num).split("e");
    var sig = ""
    if(+arr[1] + scale > 0) {
      sig = "+";
    }
    return +(Math.round(+arr[0] + "e" + sig + (+arr[1] + scale)) + "e-" + scale);
  }
}

https://plnkr.co/edit/uau8BlS1cqbvWPCHJeOy?p=preview

Solution 2 est d'éviter les calculs frontaux et de tirer des valeurs arrondies à partir du serveur principal.


2319
2017-10-11 00:27



Vous pouvez utiliser

function roundToTwo(num) {    
    return +(Math.round(num + "e+2")  + "e-2");
}

Je l'ai trouvé sur MDN. Leur façon évite le problème avec 1.005 qui était mentionné.

roundToTwo(1.005)
1.01
roundToTwo(10)
10
roundToTwo(1.7777777)
1.78
roundToTwo(9.1)
9.1
roundToTwo(1234.5678)
1234.57

323
2017-08-21 12:56



La réponse de MarkG est la bonne. Voici une extension générique pour n'importe quel nombre de décimales.

Number.prototype.round = function(places) {
  return +(Math.round(this + "e+" + places)  + "e-" + places);
}

Usage:

var n = 1.7777;    
n.round(2); // 1.78

Test de l'unité:

it.only('should round floats to 2 places', function() {

  var cases = [
    { n: 10,      e: 10,    p:2 },
    { n: 1.7777,  e: 1.78,  p:2 },
    { n: 1.005,   e: 1.01,  p:2 },
    { n: 1.005,   e: 1,     p:0 },
    { n: 1.77777, e: 1.8,   p:1 }
  ]

  cases.forEach(function(testCase) {
    var r = testCase.n.round(testCase.p);
    assert.equal(r, testCase.e, 'didn\'t get right number');
  });
})

115
2017-11-01 07:40



On peut utiliser .toFixed(NumberOfDecimalPlaces).

var str = 10.234.toFixed(2); // => '10.23'
var number = Number(str); // => 10.23

69
2017-10-21 17:02



Une méthode d'arrondi précise. La source: Mozilla

(function(){

    /**
     * Decimal adjustment of a number.
     *
     * @param   {String}    type    The type of adjustment.
     * @param   {Number}    value   The number.
     * @param   {Integer}   exp     The exponent (the 10 logarithm of the adjustment base).
     * @returns {Number}            The adjusted value.
     */
    function decimalAdjust(type, value, exp) {
        // If the exp is undefined or zero...
        if (typeof exp === 'undefined' || +exp === 0) {
            return Math[type](value);
        }
        value = +value;
        exp = +exp;
        // If the value is not a number or the exp is not an integer...
        if (isNaN(value) || !(typeof exp === 'number' && exp % 1 === 0)) {
            return NaN;
        }
        // Shift
        value = value.toString().split('e');
        value = Math[type](+(value[0] + 'e' + (value[1] ? (+value[1] - exp) : -exp)));
        // Shift back
        value = value.toString().split('e');
        return +(value[0] + 'e' + (value[1] ? (+value[1] + exp) : exp));
    }

    // Decimal round
    if (!Math.round10) {
        Math.round10 = function(value, exp) {
            return decimalAdjust('round', value, exp);
        };
    }
    // Decimal floor
    if (!Math.floor10) {
        Math.floor10 = function(value, exp) {
            return decimalAdjust('floor', value, exp);
        };
    }
    // Decimal ceil
    if (!Math.ceil10) {
        Math.ceil10 = function(value, exp) {
            return decimalAdjust('ceil', value, exp);
        };
    }
})();

Exemples:

// Round
Math.round10(55.55, -1); // 55.6
Math.round10(55.549, -1); // 55.5
Math.round10(55, 1); // 60
Math.round10(54.9, 1); // 50
Math.round10(-55.55, -1); // -55.5
Math.round10(-55.551, -1); // -55.6
Math.round10(-55, 1); // -50
Math.round10(-55.1, 1); // -60
Math.round10(1.005, -2); // 1.01 -- compare this with Math.round(1.005*100)/100 above
// Floor
Math.floor10(55.59, -1); // 55.5
Math.floor10(59, 1); // 50
Math.floor10(-55.51, -1); // -55.6
Math.floor10(-51, 1); // -60
// Ceil
Math.ceil10(55.51, -1); // 55.6
Math.ceil10(51, 1); // 60
Math.ceil10(-55.59, -1); // -55.5
Math.ceil10(-59, 1); // -50

54
2017-08-01 08:02



Aucune des réponses trouvées ici n'est correcte. @stinkycheeseman a demandé à rassembler, vous avez tous arrondi le nombre.

Pour arrondir, utilisez ceci:

Math.ceil(num * 100)/100;

53
2018-06-13 09:35