Định dạng một số có chính xác hai số thập phân trong JavaScript


571

Tôi có dòng mã này làm tròn số của tôi đến hai chữ số thập phân. Nhưng tôi nhận được các số như thế này: 10.8, 2.4, v.v ... Đây không phải là ý tưởng của tôi về hai chữ số thập phân, vậy làm thế nào tôi có thể cải thiện những điều sau đây?

Math.round(price*Math.pow(10,2))/Math.pow(10,2);

Tôi muốn các số như 10.80, 2.40, v.v ... Sử dụng jQuery là tốt với tôi.


1
Mã của bạn chính xác là những gì tôi đang tìm kiếm (để giảm độ chính xác float xuống 7 vị trí thập phân cho tệp JSON nhỏ hơn) Bỏ qua Math.pow cho speed val = Math.round (val * 10000000) / 10000000);
Pawel

Khi câu trả lời hiện-được chấp nhận cho coi là một kết quả sai cho một loạt các giá trị nhờ vào tình tiết tăng nặng không chính xác vốn có trong những con số ( 0.565, 0.575, 1.005), tôi có thể đề nghị xem xét lại tại câu trả lời này , mà được họ có đúng không?
TJ Crowder

Có thể bạn muốn bao gồm một thư viện sprintf cho JavaScript stackoverflow.com/questions/610406/
Khăn

Sau khi làm tròn chính xác với phương pháp làm tròn và làm tròn vị trí thập phân, bạn có thể sử dụng number.toFixed(x)phương thức để chuyển đổi nó thành một chuỗi với số lượng không cần thiết. Ví dụ như vòng 1.34để 1.3có phương pháp cross-browser sau đó thêm 1 zero và chuyển đổi sang chuỗi với 1.3.toFixed(2)(để có được "1.30").
Edward

Câu trả lời:


999

Để định dạng một số bằng cách sử dụng ký hiệu điểm cố định, bạn chỉ cần sử dụng phương thức toFixed :

(10.8).toFixed(2); // "10.80"

var num = 2.4;
alert(num.toFixed(2)); // "2.40"

Lưu ý rằng toFixed()trả về một chuỗi.

QUAN TRỌNG : Lưu ý rằng toFixed không làm tròn 90% thời gian, nó sẽ trả về giá trị làm tròn, nhưng trong nhiều trường hợp, nó không hoạt động.

Ví dụ:

2.005.toFixed(2) === "2.00"

CẬP NHẬT:

Ngày nay, bạn có thể sử dụng hàm Intl.NumberFormattạo. Đây là một phần của Đặc tả API quốc tế hóa ECMAScript (ECMA402). Nó có hỗ trợ trình duyệt tốt đẹp , kể cả thậm chí IE11, và nó được hỗ trợ đầy đủ trong Node.js .

const formatter = new Intl.NumberFormat('en-US', {
   minimumFractionDigits: 2,      
   maximumFractionDigits: 2,
});

console.log(formatter.format(2.005)); // "2.01"
console.log(formatter.format(1.345)); // "1.35"

Bạn cũng có thể sử dụng toLocaleStringphương thức mà bên trong sẽ sử dụng IntlAPI:

const format = (num, decimals) => num.toLocaleString('en-US', {
   minimumFractionDigits: 2,      
   maximumFractionDigits: 2,
});


console.log(format(2.005)); // "2.01"
console.log(format(1.345)); // "1.35"

API này cũng cung cấp cho bạn nhiều tùy chọn để định dạng, như hàng nghìn dấu phân cách, ký hiệu tiền tệ, v.v.


17
Không hoạt động nhất quán trên tất cả các trình duyệt, tức là (0.09).toFixed(1);cho 0,0 trong IE8
ajbeaven

41
Đã sửa không làm tròn, bạn có thể thực hiện trước: (Math.round (0.09)). toFixed (1);
thiệu

32
@rekans: Điều này sai. Math.Round(0.09)sẽ trở lại 0vì vậy điều này sẽ luôn luôn cho 0.0...
Chris

28
Đây là một ý tưởng tồi trong hầu hết các tình huống, nó chuyển đổi số thành một chuỗi hoặc số dấu phẩy động trong một số trường hợp.
Ash Blue

80
Phải đồng ý với @AshBlue tại đây ... điều này chỉ an toàn để định dạng trình bày các giá trị. Có thể phá mã với các tính toán thêm. Nếu không thì Math.round(value*100)/100hoạt động tốt hơn cho 2DP.
UpTheCux

98

Đây là một chủ đề cũ nhưng vẫn được Google xếp hạng hàng đầu và các giải pháp được cung cấp có chung vấn đề về số thập phân dấu phẩy động. Đây là chức năng (rất chung chung) mà tôi sử dụng, nhờ MDN :

function round(value, exp) {
  if (typeof exp === 'undefined' || +exp === 0)
    return Math.round(value);

  value = +value;
  exp = +exp;

  if (isNaN(value) || !(typeof exp === 'number' && exp % 1 === 0))
    return NaN;

  // Shift
  value = value.toString().split('e');
  value = Math.round(+(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));
}

Như chúng ta có thể thấy, chúng ta không gặp phải những vấn đề này:

round(1.275, 2);   // Returns 1.28
round(1.27499, 2); // Returns 1.27

Sự hào phóng này cũng cung cấp một số thứ hay ho:

round(1234.5678, -2);   // Returns 1200
round(1.2345678e+2, 2); // Returns 123.46
round("123.45");        // Returns 123

Bây giờ, để trả lời câu hỏi của OP, người ta phải gõ:

round(10.8034, 2).toFixed(2); // Returns "10.80"
round(10.8, 2).toFixed(2);    // Returns "10.80"

Hoặc, cho một chức năng ngắn gọn hơn, ít chung chung hơn:

function round2Fixed(value) {
  value = +value;

  if (isNaN(value))
    return NaN;

  // Shift
  value = value.toString().split('e');
  value = Math.round(+(value[0] + 'e' + (value[1] ? (+value[1] + 2) : 2)));

  // Shift back
  value = value.toString().split('e');
  return (+(value[0] + 'e' + (value[1] ? (+value[1] - 2) : -2))).toFixed(2);
}

Bạn có thể gọi nó bằng:

round2Fixed(10.8034); // Returns "10.80"
round2Fixed(10.8);    // Returns "10.80"

Các ví dụ và bài kiểm tra khác nhau (nhờ @ tj-crowder !):


1
Làm thế nào không có một cách đơn giản để làm điều này? ES6 để giải cứu?
zero_cool

Cảm ơn bạn đã đăng bài polyfill MDN. Trên trang MDN được liên kết, polyfill không còn ở đó nữa. Tôi tự hỏi tại sao nó bị xóa ...
King Holly

43

Tôi thường thêm nó vào thư viện cá nhân của mình và sau một số gợi ý và sử dụng giải pháp @TIMINeutron cũng vậy, và làm cho nó có thể thích ứng với độ dài thập phân sau đó, điều này phù hợp nhất:

function precise_round(num, decimals) {
   var t = Math.pow(10, decimals);   
   return (Math.round((num * t) + (decimals>0?1:0)*(Math.sign(num) * (10 / Math.pow(100, decimals)))) / t).toFixed(decimals);
}

sẽ làm việc cho các trường hợp ngoại lệ được báo cáo.


2
chính xác (1.275,2) là 1,27?
allenhwkim

2
@Imre Thay đổi giá trị trả về thành (Math.round (num * Math.pow (10, số thập phân)) / Math.pow (10, số thập phân)). ToFixed (2); và bạn sẽ không còn có vấn đề đó.
dkroy

6
bạn khai báo "dấu" và "dec" ở đâu nếu chức năng thứ hai của bạn được chọn vì không nên xác định chúng là không xác định?
Ady Ngom

2
Tôi đã thêm một cách khắc phục cho phương thức ký hiệu sai trong IE: gist.github.com/ArminVieweg/28647e735aa6efaba401
Armin

1
@Armin Bản sửa lỗi của bạn cũng làm cho nó hoạt động trong Safari. Chức năng ban đầu không hoạt động trong Safari.
Dave

19

Tôi không biết tại sao tôi không thể thêm nhận xét vào câu trả lời trước đó (có thể tôi bị mù một cách vô vọng, dunno), nhưng tôi đã đưa ra một giải pháp sử dụng câu trả lời của @ Miguel:

function precise_round(num,decimals) {
   return Math.round(num*Math.pow(10, decimals)) / Math.pow(10, decimals);
}

Và hai bình luận của nó (từ @bighostkim và @Imre):

  • Vấn đề precise_round(1.275,2)không trả lại 1.28
  • Vấn đề với việc precise_round(6,2)không trả lại 6,00 (như anh ta muốn).

Giải pháp cuối cùng của tôi là như sau:

function precise_round(num,decimals) {
    var sign = num >= 0 ? 1 : -1;
    return (Math.round((num*Math.pow(10,decimals)) + (sign*0.001)) / Math.pow(10,decimals)).toFixed(decimals);
}

Như bạn có thể thấy tôi đã phải thêm một chút "hiệu chỉnh" (nó không phải là cái gì, nhưng vì Math.round bị mất - bạn có thể kiểm tra nó trên jsfiddle.net - đây là cách duy nhất tôi biết cách "sửa "Nó). Nó thêm 0,001 vào số đã được đệm, do đó, nó thêm 1ba 0s ở bên phải của giá trị thập phân. Vì vậy, nó nên được an toàn để sử dụng.

Sau đó tôi đã thêm vào .toFixed(decimal)để luôn xuất số theo đúng định dạng (với số thập phân đúng).

Vì vậy, đó là khá nhiều đó. Sử dụng nó tốt ;)

EDIT: thêm chức năng để "hiệu chỉnh" các số âm.


2
"Hiệu chỉnh" hầu hết là an toàn, nhưng ví dụ precise_round(1.27499,2)bây giờ cũng trả về 1,28 ... Không phải Math.roundlà mất mát; cách mà máy tính lưu trữ bên trong các giá trị dấu phẩy động là. Về cơ bản, bạn chắc chắn sẽ thất bại với một số giá trị trước khi dữ liệu thậm chí đến chức năng của bạn :)
Imre

@Imre, bạn tuyệt đối đúng. Đó là lý do tại sao tôi giải thích 0,001 này đang làm gì ở đó, trong trường hợp bất cứ ai muốn làm cho nó "nhiều hơn chính xác hơn " hoặc thậm chí xóa nó (nếu bạn tình cờ có một siêu máy tính với 2 Mbyte mỗi lần nổi, tôi không nghĩ có ai ở đây ;)
tfrascaroli

1
Trên thực tế, đặc tả ngôn ngữ khá cụ thể về việc sử dụng 64 bit cho các giá trị số, do đó, việc có / sử dụng siêu máy tính sẽ không thay đổi gì cả :)
Imre

đối với 0,001, bạn có thể thay thế bằng cách thêm nhiều số không theo độ dài của số thập phân. vì vậy ..
Miguel

15

Một cách để chắc chắn 100% rằng bạn nhận được một số có 2 số thập phân:

(Math.round(num*100)/100).toFixed(2)

Nếu điều này gây ra lỗi làm tròn, bạn có thể sử dụng như sau như James đã giải thích trong nhận xét của mình:

(Math.round((num * 1000)/10)/100).toFixed(2)

6
Đây là cách tốt nhất, đơn giản nhất để làm điều đó. Tuy nhiên, do toán học dấu phẩy động, 1.275 * 100 = 127.49999999999999, có thể gây ra các lỗi nhỏ trong làm tròn số. Để khắc phục điều này, chúng ta có thể nhân 1000 và chia cho 10, như (1.275 * 1000) / 10 = 127.5. Như sau: var answer = (Math.round((num * 1000)/10)/100).toFixed(2);
James Gould

(Math.round ((1.015 * 1000) / 10) / 100) .toFixed (2) vẫn cho 1.01, không nên là 1.02?
gaurav5430

14

toFixed (n) cung cấp n độ dài sau dấu thập phân; toPrecision (x) cung cấp x tổng chiều dài.

Sử dụng phương pháp này dưới đây

// Example: toPrecision(4) when the number has 7 digits (3 before, 4 after)
    // It will round to the tenths place
    num = 500.2349;
    result = num.toPrecision(4); // result will equal 500.2

VÀ nếu bạn muốn số được sử dụng cố định

result = num.toFixed(2);

nó không hoạt động tốt ... đối với số num = 50,2349, bạn nên viết vào phần Ghi chú (3) để nhận 50,2
Piotr Czyż

nó chỉ là một ví dụ bạn có thể thay đổi nó theo nhu cầu của bạn @ PiotrCzyż
Syed Umar Ahmed

5

Tôi đã không tìm thấy một giải pháp chính xác cho vấn đề này, vì vậy tôi đã tạo ra giải pháp của riêng mình:

function inprecise_round(value, decPlaces) {
  return Math.round(value*Math.pow(10,decPlaces))/Math.pow(10,decPlaces);
}

function precise_round(value, decPlaces){
    var val = value * Math.pow(10, decPlaces);
    var fraction = (Math.round((val-parseInt(val))*10)/10);

    //this line is for consistency with .NET Decimal.Round behavior
    // -342.055 => -342.06
    if(fraction == -0.5) fraction = -0.6;

    val = Math.round(parseInt(val) + fraction) / Math.pow(10, decPlaces);
    return val;
}

Ví dụ:

function inprecise_round(value, decPlaces) {
  return Math.round(value * Math.pow(10, decPlaces)) / Math.pow(10, decPlaces);
}

function precise_round(value, decPlaces) {
  var val = value * Math.pow(10, decPlaces);
  var fraction = (Math.round((val - parseInt(val)) * 10) / 10);

  //this line is for consistency with .NET Decimal.Round behavior
  // -342.055 => -342.06
  if (fraction == -0.5) fraction = -0.6;

  val = Math.round(parseInt(val) + fraction) / Math.pow(10, decPlaces);
  return val;
}

// This may produce different results depending on the browser environment
console.log("342.055.toFixed(2)         :", 342.055.toFixed(2)); // 342.06 on Chrome & IE10

console.log("inprecise_round(342.055, 2):", inprecise_round(342.055, 2)); // 342.05
console.log("precise_round(342.055, 2)  :", precise_round(342.055, 2));   // 342.06
console.log("precise_round(-342.055, 2) :", precise_round(-342.055, 2));  // -342.06

console.log("inprecise_round(0.565, 2)  :", inprecise_round(0.565, 2));   // 0.56
console.log("precise_round(0.565, 2)    :", precise_round(0.565, 2));     // 0.57


2
Cảm ơn. Đây là một cách khéo léo để kiểm tra điều này: jsfiddle.net/lamarant/ySXuF . Tôi đang áp dụng toFixed () cho giá trị trước khi trả lại giá trị đó nối thêm số 0 chính xác vào cuối giá trị được trả về.
lamarant

không hoạt động với giá trị = 0,004990845956707237 và inprecise_round (value, 8) trả về 0,00499085 nhưng phải trả lại 0,00499084
MERT DOĞAN

3

@heridev và tôi đã tạo một hàm nhỏ trong jQuery.

Bạn có thể thử tiếp theo:

HTML

<input type="text" name="one" class="two-digits"><br>
<input type="text" name="two" class="two-digits">​

jQuery

// apply the two-digits behaviour to elements with 'two-digits' as their class
$( function() {
    $('.two-digits').keyup(function(){
        if($(this).val().indexOf('.')!=-1){         
            if($(this).val().split(".")[1].length > 2){                
                if( isNaN( parseFloat( this.value ) ) ) return;
                this.value = parseFloat(this.value).toFixed(2);
            }  
         }            
         return this; //for chaining
    });
});

DEMO TRỰC TUYẾN:

http://jsfiddle.net/c4Wqn/


1
Tôi có thể đánh giá cao sự đóng góp, mặc dù tôi nghĩ rằng việc thêm các phần tử DOM và jQuery vào hỗn hợp dường như nằm ngoài phạm vi của câu hỏi.
Chris May 5 tháng

Bạn không nên nghe sự kiện keyup, vì nó trông rất tệ và không kích hoạt khi bạn thêm một cái gì đó với tập lệnh. Tôi thích nghe inputsự kiện này. Điều này không tạo ra hiệu ứng nhấp nháy và cũng kích hoạt khi bạn truy cập vào trường bằng JS
Le 'nton

3

Vấn đề với các giá trị dấu phẩy động là chúng đang cố gắng biểu diễn một lượng vô hạn các giá trị (liên tục) với một lượng bit cố định. Vì vậy, một cách tự nhiên, phải có một số mất mát khi chơi và bạn sẽ bị cắn với một số giá trị.

Khi một máy tính lưu trữ 1.275 dưới dạng giá trị dấu phẩy động, thực tế nó sẽ không nhớ đó là 1.275 hay 1.27499999999999993 hay thậm chí 1.27500000000000002. Các giá trị này sẽ cho kết quả khác nhau sau khi làm tròn đến hai số thập phân, nhưng chúng sẽ không, vì đối với máy tính, chúng trông giống hệt nhau sau khi lưu trữ dưới dạng giá trị dấu phẩy động và không có cách nào để khôi phục dữ liệu bị mất. Bất kỳ tính toán thêm sẽ chỉ tích lũy sự thiếu chính xác như vậy.

Vì vậy, nếu độ chính xác quan trọng, bạn phải tránh các giá trị dấu phẩy động ngay từ đầu. Các tùy chọn đơn giản nhất là

  • sử dụng một thư viện dành riêng
  • sử dụng các chuỗi để lưu trữ và chuyển xung quanh các giá trị (kèm theo các thao tác chuỗi)
  • sử dụng số nguyên (ví dụ: bạn có thể chuyển khoảng số phần trăm giá trị thực của mình, ví dụ: số tiền tính bằng xu thay vì số tiền tính bằng đô la)

Ví dụ: khi sử dụng số nguyên để lưu trữ số phần trăm, hàm tìm giá trị thực khá đơn giản:

function descale(num, decimals) {
    var hasMinus = num < 0;
    var numString = Math.abs(num).toString();
    var precedingZeroes = '';
    for (var i = numString.length; i <= decimals; i++) {
        precedingZeroes += '0';
    }
    numString = precedingZeroes + numString;
    return (hasMinus ? '-' : '') 
        + numString.substr(0, numString.length-decimals) 
        + '.' 
        + numString.substr(numString.length-decimals);
}

alert(descale(127, 2));

Với các chuỗi, bạn sẽ cần làm tròn, nhưng vẫn có thể quản lý được:

function precise_round(num, decimals) {
    var parts = num.split('.');
    var hasMinus = parts.length > 0 && parts[0].length > 0 && parts[0].charAt(0) == '-';
    var integralPart = parts.length == 0 ? '0' : (hasMinus ? parts[0].substr(1) : parts[0]);
    var decimalPart = parts.length > 1 ? parts[1] : '';
    if (decimalPart.length > decimals) {
        var roundOffNumber = decimalPart.charAt(decimals);
        decimalPart = decimalPart.substr(0, decimals);
        if ('56789'.indexOf(roundOffNumber) > -1) {
            var numbers = integralPart + decimalPart;
            var i = numbers.length;
            var trailingZeroes = '';
            var justOneAndTrailingZeroes = true;
            do {
                i--;
                var roundedNumber = '1234567890'.charAt(parseInt(numbers.charAt(i)));
                if (roundedNumber === '0') {
                    trailingZeroes += '0';
                } else {
                    numbers = numbers.substr(0, i) + roundedNumber + trailingZeroes;
                    justOneAndTrailingZeroes = false;
                    break;
                }
            } while (i > 0);
            if (justOneAndTrailingZeroes) {
                numbers = '1' + trailingZeroes;
            }
            integralPart = numbers.substr(0, numbers.length - decimals);
            decimalPart = numbers.substr(numbers.length - decimals);
        }
    } else {
        for (var i = decimalPart.length; i < decimals; i++) {
            decimalPart += '0';
        }
    }
    return (hasMinus ? '-' : '') + integralPart + (decimals > 0 ? '.' + decimalPart : '');
}

alert(precise_round('1.275', 2));
alert(precise_round('1.27499999999999993', 2));

Lưu ý rằng chức năng này làm tròn đến gần nhất, liên kết từ 0 , trong khi IEEE 754 khuyến nghị làm tròn đến gần nhất, liên kết ngay cả với tư cách là hành vi mặc định cho các hoạt động của dấu phẩy động. Những sửa đổi như vậy được để lại như một bài tập cho người đọc :)


3

Đây là một đơn giản

function roundFloat(num,dec){
    var d = 1;
    for (var i=0; i<dec; i++){
        d += "0";
    }
    return Math.round(num * d) / d;
}

Sử dụng như alert(roundFloat(1.79209243929,4));

Jsfiddle


2

Làm tròn giá trị thập phân của bạn, sau đó sử dụng toFixed(x)cho (các) chữ số dự kiến ​​của bạn.

function parseDecimalRoundAndFixed(num,dec){
  var d =  Math.pow(10,dec);
  return (Math.round(num * d) / d).toFixed(dec);
}

Gọi

parseDecimalRoundAndFixed (10.800243929,4) => 10,80 parseDecimalRoundAndFixed (10.807243929,2) => 10,81


2

Làm tròn xuống

function round_down(value, decPlaces) {
    return Math.floor(value * Math.pow(10, decPlaces)) / Math.pow(10, decPlaces);
}

Làm tròn

function round_up(value, decPlaces) {
    return Math.ceil(value * Math.pow(10, decPlaces)) / Math.pow(10, decPlaces);
}

Vòng gần nhất

function round_nearest(value, decPlaces) {
    return Math.round(value * Math.pow(10, decPlaces)) / Math.pow(10, decPlaces);
}

Đã hợp nhất https://stackoverflow.com/a/7641824/1889449https://www.kirupa.com/html5/rounding_numbers_in_javascript.htmlm Cảm ơn họ.


2

/**
 * 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 +ve 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

// testing some -ve 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


2

Đây là giải pháp 1 dòng của tôi: Number((yourNumericValueHere).toFixed(2));

Đây là những gì xảy ra:

1) Trước tiên, bạn áp dụng .toFixed(2)vào số mà bạn muốn làm tròn số thập phân của. Lưu ý rằng điều này sẽ chuyển đổi giá trị thành một chuỗi từ số. Vì vậy, nếu bạn đang sử dụng Bản mô tả, nó sẽ đưa ra một lỗi như thế này:

"Nhập 'chuỗi' không thể gán cho loại 'số'"

2) Để lấy lại giá trị số hoặc chuyển đổi chuỗi thành giá trị số, chỉ cần áp dụng Number() hàm trên giá trị được gọi là 'chuỗi' đó.

Để làm rõ, hãy xem ví dụ dưới đây:

VÍ DỤ: Tôi có một số tiền có tối đa 5 chữ số ở vị trí thập phân và tôi muốn rút ngắn nó xuống tối đa 2 chữ số thập phân. Tôi làm như vậy:

var price = 0.26453;
var priceRounded = Number((price).toFixed(2));
console.log('Original Price: ' + price);
console.log('Price Rounded: ' + priceRounded);


1

Đặt những điều sau đây trong một số phạm vi toàn cầu:

Number.prototype.getDecimals = function ( decDigCount ) {
   return this.toFixed(decDigCount);
}

sau đó thử :

var a = 56.23232323;
a.getDecimals(2); // will return 56.23

Cập nhật

Lưu ý rằng toFixed()chỉ có thể hoạt động với số lượng thập phân giữa 0-20tức là a.getDecimals(25)có thể tạo ra lỗi javascript, do đó, để bổ sung rằng bạn có thể thêm một số kiểm tra bổ sung tức là

Number.prototype.getDecimals = function ( decDigCount ) {
   return ( decDigCount > 20 ) ? this : this.toFixed(decDigCount);
}

1
Number(((Math.random() * 100) + 1).toFixed(2))

điều này sẽ trả về một số ngẫu nhiên từ 1 đến 100 được làm tròn đến 2 chữ số thập phân.



1

Sử dụng phản hồi này bằng cách tham khảo: https://stackoverflow.com/a/21029698/454827

Tôi xây dựng một hàm để có được số thập phân động:

function toDec(num, dec)
{
        if(typeof dec=='undefined' || dec<0)
                dec = 2;

        var tmp = dec + 1;
        for(var i=1; i<=tmp; i++)
                num = num * 10;

        num = num / 10;
        num = Math.round(num);
        for(var i=1; i<=dec; i++)
                num = num / 10;

        num = num.toFixed(dec);

        return num;
}

ví dụ làm việc ở đây: https://jsfiddle.net/wpxLduLc/


1

parse = function (data) {
       data = Math.round(data*Math.pow(10,2))/Math.pow(10,2);
       if (data != null) {
            var lastone = data.toString().split('').pop();
            if (lastone != '.') {
                 data = parseFloat(data);
            }
       }
       return data;
  };

$('#result').html(parse(200)); // output 200
$('#result1').html(parse(200.1)); // output 200.1
$('#result2').html(parse(200.10)); // output 200.1
$('#result3').html(parse(200.109)); // output 200.11
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<div id="result"></div>
<div id="result1"></div>
<div id="result2"></div>
<div id="result3"></div>


1

Với các ví dụ này, bạn vẫn sẽ gặp lỗi khi thử làm tròn số 1.005, giải pháp là sử dụng thư viện như Math.js hoặc hàm này:

function round(value: number, decimals: number) {
    return Number(Math.round(value + 'e' + decimals) + 'e-' + decimals);
}

1

Tôi đã nhận được một số ý tưởng từ bài đăng này vài tháng trước, nhưng không có câu trả lời nào ở đây, cũng như câu trả lời từ các bài đăng / blog khác có thể xử lý tất cả các tình huống (ví dụ: số âm và một số "số may mắn" mà người thử nghiệm của chúng tôi đã tìm thấy). Cuối cùng, người thử nghiệm của chúng tôi không tìm thấy bất kỳ vấn đề nào với phương pháp này dưới đây. Dán một đoạn mã của tôi:

fixPrecision: function (value) {
    var me = this,
        nan = isNaN(value),
        precision = me.decimalPrecision;

    if (nan || !value) {
        return nan ? '' : value;
    } else if (!me.allowDecimals || precision <= 0) {
        precision = 0;
    }

    //[1]
    //return parseFloat(Ext.Number.toFixed(parseFloat(value), precision));
    precision = precision || 0;
    var negMultiplier = value < 0 ? -1 : 1;

    //[2]
    var numWithExp = parseFloat(value + "e" + precision);
    var roundedNum = parseFloat(Math.round(Math.abs(numWithExp)) + 'e-' + precision) * negMultiplier;
    return parseFloat(roundedNum.toFixed(precision));
},

Tôi cũng có nhận xét mã (xin lỗi tôi đã quên tất cả các chi tiết rồi) ... Tôi đang đăng câu trả lời của mình lên đây để tham khảo trong tương lai:

9.995 * 100 = 999.4999999999999
Whereas 9.995e2 = 999.5
This discrepancy causes Math.round(9.995 * 100) = 999 instead of 1000.
Use e notation instead of multiplying /dividing by Math.Pow(10,precision).

0

Tôi đang sửa vấn đề sửa đổi. Chỉ hỗ trợ 2 số thập phân.

$(function(){
  //input number only.
  convertNumberFloatZero(22); // output : 22.00
  convertNumberFloatZero(22.5); // output : 22.50
  convertNumberFloatZero(22.55); // output : 22.55
  convertNumberFloatZero(22.556); // output : 22.56
  convertNumberFloatZero(22.555); // output : 22.55
  convertNumberFloatZero(22.5541); // output : 22.54
  convertNumberFloatZero(22222.5541); // output : 22,222.54

  function convertNumberFloatZero(number){
	if(!$.isNumeric(number)){
		return 'NaN';
	}
	var numberFloat = number.toFixed(3);
	var splitNumber = numberFloat.split(".");
	var cNumberFloat = number.toFixed(2);
	var cNsplitNumber = cNumberFloat.split(".");
	var lastChar = splitNumber[1].substr(splitNumber[1].length - 1);
	if(lastChar > 0 && lastChar < 5){
		cNsplitNumber[1]--;
	}
	return Number(splitNumber[0]).toLocaleString('en').concat('.').concat(cNsplitNumber[1]);
  };
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>


0
(Math.round((10.2)*100)/100).toFixed(2)

Điều đó sẽ mang lại: 10.20

(Math.round((.05)*100)/100).toFixed(2)

Điều đó sẽ mang lại: 0.05

(Math.round((4.04)*100)/100).toFixed(2)

Điều đó sẽ mang lại: 4.04

Vân vân.


0

/*Due to all told stuff. You may do 2 things for different purposes:
When showing/printing stuff use this in your alert/innerHtml= contents:
YourRebelNumber.toFixed(2)*/

var aNumber=9242.16;
var YourRebelNumber=aNumber-9000;
alert(YourRebelNumber);
alert(YourRebelNumber.toFixed(2));

/*and when comparing use:
Number(YourRebelNumber.toFixed(2))*/

if(YourRebelNumber==242.16)alert("Not Rounded");
if(Number(YourRebelNumber.toFixed(2))==242.16)alert("Rounded");

/*Number will behave as you want in that moment. After that, it'll return to its defiance.
*/


0

Điều này rất đơn giản và hoạt động tốt như bất kỳ ai khác:

function parseNumber(val, decimalPlaces) {
    if (decimalPlaces == null) decimalPlaces = 0
    var ret = Number(val).toFixed(decimalPlaces)
    return Number(ret)
}

Vì toFixed () chỉ có thể được gọi trên các số và không may trả về một chuỗi, nên tất cả các phân tích cú pháp cho bạn theo cả hai hướng. Bạn có thể truyền một chuỗi hoặc một số và bạn sẽ nhận được một số mỗi lần! Gọi parseNumber (1.49) sẽ cung cấp cho bạn 1 và parseNumber (1.49,2) sẽ cung cấp cho bạn 1,50. Giống như những người giỏi nhất của họ!


0

Bạn cũng có thể sử dụng .toPrecision()phương thức và một số mã tùy chỉnh và luôn làm tròn đến chữ số thập phân thứ n bất kể độ dài của phần int.

function glbfrmt (number, decimals, seperator) {
    return typeof number !== 'number' ? number : number.toPrecision( number.toString().split(seperator)[0].length + decimals);
}

Bạn cũng có thể làm cho nó một plugin để sử dụng tốt hơn.



-2

Tôi tìm thấy một cách rất đơn giản để giải quyết vấn đề này cho tôi và có thể được sử dụng hoặc điều chỉnh:

td[row].innerHTML = price.toPrecision(price.toFixed(decimals).length

-4

Làm việc 100% !!! Thử nó

<html>
     <head>
      <script>
      function replacePonto(){
        var input = document.getElementById('qtd');
        var ponto = input.value.split('.').length;
        var slash = input.value.split('-').length;
        if (ponto > 2)
                input.value=input.value.substr(0,(input.value.length)-1);

        if(slash > 2)
                input.value=input.value.substr(0,(input.value.length)-1);

        input.value=input.value.replace(/[^0-9.-]/,'');

        if (ponto ==2)
	input.value=input.value.substr(0,(input.value.indexOf('.')+3));

if(input.value == '.')
	input.value = "";
              }
      </script>
      </head>
      <body>
         <input type="text" id="qtd" maxlength="10" style="width:140px" onkeyup="return replacePonto()">
      </body>
    </html>


Chào mừng đến với SO. Xin vui lòng đọc này như thế nào để trả lời và làm theo hướng dẫn để trả lời.
thewaywewere
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.