文章目录
一、抛砖引玉:金额转Number1. 问题2. 原因3. 解决
二、深入探讨:Number转金额1. 方式一2. 方式二:使用正则3. 方式三:字符串截取4. 方式四:Intl.NumberFormat,
一、抛砖引玉:金额转Number
1. 问题
parseFloat 时 120,000.00 取到的值是120
2. 原因
问题的原因在于 JavaScript 在解析带有逗号或点号的数字字符串时会认为逗号或点号为千位分隔符或小数点符号,因此不会同样对待这些字符,因而出现了解析出错误的情况。
3. 解决
要完整地将 120,000.00 取出并解析为数字,可以先将逗号 , 替换为空字符串 ‘’,然后再使用 parseFloat() 或 parseInt() 等函数将字符串解析为数值。 const numString = '120,000.00';
const num = parseFloat(numString.replace(/,/g, ''));
console.log(num); // 120000
在这段代码中,我们使用了 String.prototype.replace() 方法将字符串中的逗号 , 替换为空字符串,然后使用 parseFloat() 方法将新字符串解析为浮点数。 如果需要将该数字字符串解析为整数(忽略小数部分),可以使用 parseInt() 函数,但需要指定第二个参数为 10,以避免解析出的数字出现意外错误。例如: const numString = '120,000.00';
const num = parseInt(numString.replace(/,/g, ''), 10);
console.log(num); // 120000
二、深入探讨:Number转金额
1. 方式一
/**
* @description : 金额格式化处理函数
* @author : 'Hukang'
* @param : money 输入的金额
* @param : symbol 金额的前缀
* @param : decimals 小数点后截取的位数,默认是两位
* @date : 2023-04-21 14:05:32
*/
const formatToFixed = (money, decimals = 2) => {
return(Math.round((parseFloat(money) + Number.EPSILON) * Math.pow(10, decimals)) / Math.pow(10, decimals)).toFixed(decimals);
};
const formatMoney = (money, symbol = "", decimals = 2) => `${symbol}${
parseFloat(formatToFixed(money, decimals)).toLocaleString("zh", {
maximumFractionDigits: decimals,
useGrouping: true
})
}`;
formatMoney(12341234.246); // 12,341,234.25
formatMoney(12341234.12345, "¥", 4); // ¥12,341,234.1235
2. 方式二:使用正则
使用正则表达式处理整数部分,小数部分同上所示。有个《JS 正则迷你书》介绍正则表达式挺好的,在 2.4.2 章就讲了“数字的千位分隔符表示法”,介绍的很详细,推荐看看。
\b:单词边界,具体就是 \w 与 \W 之间的位置,也包括 \w 与 ^ 之间的位置,和 \w 与 $ 之间的位置\B :\b 的反面的意思,非单词边界(?=p):其中 p 是一个子模式,即 p 前面的位置,或者说,该位置后面的字符要匹配 p
初步 /**
* @params {Number} money 金额
* @params {Number} decimals 保留小数点后位数
* @params {String} symbol 前置符号
*/
const formatMoney = (money, symbol = "", decimals = 2) => {
let result = money
.toFixed(decimals)
.replace(/\B(?=(\d{3})+\b)/g, ",")
.replace(/^/, `${symbol}`);
return result;
};
formatMoney(12341234.246, "$", 2); // $12,341,234.25
优化:解决toFixed()问题 /**
* @description : 金额格式化处理函数
* @author : 'Hukang'
* @param : money 输入的金额
* @param : symbol 金额的前缀
* @param : decimals 小数点后截取的位数,默认是两位
* @date : 2023-04-21 14:05:32
*/
const formatToFixed = (money, decimals = 2) => {
return(Math.round((parseFloat(money) + Number.EPSILON) * Math.pow(10, decimals)) / Math.pow(10, decimals)).toFixed(decimals);
};
const formatMoneyNew = (money, symbol = "", decimals = 2) =>
formatToFixed(money, decimals)
.replace(/\B(?=(\d{3})+\b)/g, ",")
.replace(/^/, `${symbol}`);
formatMoneyNew(12341234.035, "¥", 2); // ¥12,341,234.04
formatMoneyNew(12341234.045, "¥", 2); // ¥12,341,234.05
3. 方式三:字符串截取
循环字符串,通过 slice 截取实现
substring(start, end):包含 start,不包含 endsubstr(start, length):包含 start,长度为 lengthslice(start, end):可操作数组和字符串;包含 start,不包含 endsplice(start, length, items):只能针对数组;增删改都可以
/**
* @description : 金额格式化处理函数
* @author : 'Hukang'
* @param : money 输入的金额
* @param : symbol 金额的前缀
* @param : decimals 小数点后截取的位数,默认是两位
* @date : 2023-04-21 14:05:32
*/
const formatToFixed = (money, decimals = 2) => {
return(Math.round((parseFloat(money) + Number.EPSILON) * Math.pow(10, decimals)) / Math.pow(10, decimals)).toFixed(decimals);
};
const formatMoney = (money, symbol = "", decimals = 2) => {
let arr = formatToFixed(money, decimals).toString().split(".");
let num = arr[0];
let first = "";
su;
while (num.length > 3) {
first = "," + num.slice(-3) + first;
num = num.slice(0, num.length - 3);
}
if (num) {
first = num + first;
}
return `${symbol} ${[first, arr[1]].join(".")}`;
};
formatMoney(12341234.246, "$", 2); // $ 12,341,234.25
formatMoney(12341234.035, "¥", 2); // ¥ 12,341,234.04
formatMoney(12341234.045, "¥", 2); // ¥ 12,341,234.05
4. 方式四:Intl.NumberFormat,
Intl.NumberFormat,用法和toLocaleString()挺相似的
const formatMoney = (money, decimals = 2) => {
return new Intl.NumberFormat("zh-CN", {
style: "currency", // 货币形式
currency: "CNY", // "CNY"是人民币
currencyDisplay: "symbol", // 默认“symbol”,中文中代表“¥”符号
// useGrouping: true, // 是否使用分组分隔符,如千位分隔符或千/万/亿分隔符,默认为true
// minimumIntegerDigits: 1, // 使用的整数数字的最小数目.可能的值是从1到21,默认值是1
// minimumFractionDigits: 2, // 使用的小数位数的最小数目.可能的值是从 0 到 20
maximumFractionDigits: decimals, // 使用的小数位数的最大数目。可能的值是从 0 到 20
}).format(money);
};
console.log(formatMoney(12341234.2, 2)); // ¥12,341,234.20
console.log(formatMoney(12341234.246, 1)); // ¥12,341,234.2
console.log(formatMoney(12341234.035, 2)); // ¥12,341,234.04
console.log(formatMoney(12341234.045, 2)); // ¥12,341,234.05
console.log(formatMoney(12341234.12335, 4)); // ¥12,341,234.1234
console.log(formatMoney(12341234.12345, 4)); // ¥12,341,234.1235
精彩文章
发表评论