16 May 2016
之前在UESTC前端群里跟一些朋友分享了一些javascript的思考题,旨在促进群内技术讨论,共同进步。期间不乏思维的火花,一直想将这些宝贵的财富沉淀下来,以便日后翻阅。
这个问题是在我在实际工作中遇到的,将后台返回的计数转化为符合英文阅读习惯的展现方式,比如将1234567表示为'1,234,567',我当时觉得有简洁的方法,但是又一时想不出来,就把这个问题丢到群里让大家讨论,最后大家给出了四种方案,当然在实际项目中,我采用了兼容性和书写优雅的最后一种,其他几种对开阔思路还是挺有好处的,希望对大家有所启示。
方案一 toLocaleString
这是javascript的Number对象的内置方法,如果没有讨厌的IE,本应该是极好的
function num2Str(num) {
// 兼容性问题,不可控IE下1234会变为'1,234.00'
return num.toLocaleString();
}
方案二 截取法
这是一种最朴素的思想,先从起始位置截断,让剩余字符串的长度为3的倍数,然后每隔3位,插入逗号分隔,然后再将截取的前缀和插入逗号的剩余字符串拼接。
function num2Str(num) {
var len, prefix, substr, index;
num += '';
len = num.length;
index = len % 3;
prefix = num.substr(0, index);
substr = num.substr(index);
return len > 3 ? (index === 0 ? '' : prefix + ',') + substr.replace(/(\d{3})(?=\d)/g, '$1,'): prefix;
}
方案三 补齐法
这是一种和方案二相反的思想,因为目标字符串只有数字和逗号为合法字符,所以考虑先用其他字符将字符串补齐到长度为3的倍数,然后每隔3位,插入逗号分隔,然后再将其他字符剔除即可。
function num2Str(num) {
var len;
num += '';
len = num.length;
index = len % 3;
return ('a'.repeat(index ? 3 - index : 0) + num).replace(/(\S{3})(?=\d)/g, '$1,').replace(/a/g, '');
};
方案四 正则正向前瞻
这个方案由群里的我怎能不变态提供
这种方法巧妙的利用了正则表达式的正向前瞻,这个思想可以扩展为任意等差数列位置插入指定字符,具体的做法就请读者自己试验了。
function num2Str(num) {
return num.replace(/(\d)(?=(?:\d{3})+$)/g, '$1,');
}
方案五 零宽断言(终极方案)
这个方案由我带的实习生提供
这种方法也是利用正则表达式的正向前瞻,和方案四思路基本一致,但更加简洁。
function num2Str(num) {
return num.replace(/(?=\B(?:\d{3})+$)/g, ',');
}