数字格式化的 js 库

数字格式化的 js 库

Numeral.js,是一个用于格式化数字处理数字的 js 库。

Tip:目前 Star 有 9.2k,5年以前就没有在更新。其文档写得不很清晰,比如它提供了多语言,但如何切换成中文,怎么使用却没有说,对于某些问题(abbreviations 报错)笔者只有从源码、更新日志和 Issues 中寻找答案。

使用它

node 中通过 npm 安装即可:

PS E:react-project> npm i numeral 

Tip:也可以在浏览器中直接通过 src 的方式使用。

创建实例

通过 numeral() 创建一个实例:

var myNumeral = numeral(1000); var value = myNumeral.value(); // value 1000 console.log('value', value) 

感觉好鸡肋,但可以取消格式化。比如将 1,000 处理成 1000

var myNumeral2 = numeral('1,000'); var value2 = myNumeral2.value(); // value2 1000 console.log('value2', value2) 

格式化

这部分是我们最关心的。比如笔者的需求有:

  • 将后台的字节数根据数值大小自动转为 KBMBGB等对应的单位
  • 数字太长,显示区域有限,比如将 123456789 转为 123.5m123.5百万

format()

通过 format() 可以将 1000 格式化成 1,000,将 123456789 格式化成 123,456,789。请看示例:

var number = numeral(1000).format('0,0'); // number:  1,000 console.log('number: ', number); var number2 = numeral(123456789).format('0,0'); // number2:  123,456,789 console.log('number2: ', number2); // 四舍五入 var number3 = numeral(1.93).format('0,0'); // number3:  2 console.log('number3: ', number3); // 四舍五入 var number4 = numeral(1.23).format('0,0'); // number4:  1 console.log('number4: ', number4); 

Tip:上面我们用了 0,0 这种格式,其他格式请直接看 numeral.js:

// node_modulesnumeraltestsnumeral.js describe('Format', function() {     it('should format to a number', function() {         var tests = [                 [0, null, '0'],                 [0, '0.00', '0.00'],                 [null, null, '0'],                 [NaN, '0.0', '0.0'],                 [1.23,'0,0','1'],                 [10000,'0,0.0000','10,000.0000'],                 [10000.23,'0,0','10,000'],                 [-10000,'0,0.0','-10,000.0'],                 [10000.1234,'0.000','10000.123'],                 [10000,'0[.]00','10000'],                 [10000.1,'0[.]00','10000.10'],                 [10000.123,'0[.]00','10000.12'],                 [10000.456,'0[.]00','10000.46'],                 [10000.001,'0[.]00','10000'],                 [10000.45,'0[.]00[0]','10000.45'],                 [10000.456,'0[.]00[0]','10000.456'],                 [10000,'(0,0.0000)','10,000.0000'],                 [-10000,'(0,0.0000)','(10,000.0000)'],                 [-12300,'+0,0.0000','-12,300.0000'],                 [1230,'+0,0','+1,230'],                 [1230,'-0,0','1,230'],                 [-1230,'-0,0','-1,230'],                 [-1230.4,'0,0.0+','1,230.4-'],                 [-1230.4,'0,0.0-','1,230.4-'],                 [1230.4,'0,0.0-','1,230.4'],                 [100.78, '0', '101'],                 [100.28, '0', '100'],                 [1.932,'0.0','1.9'],                 [1.9687,'0','2'],                 [1.9687,'0.0','2.0'],                 [-0.23,'.00','-.23'],                 [-0.23,'(.00)','(.23)'],                 [0.23,'0.00000','0.23000'],                 [0.67,'0.0[0000]','0.67'],                 [3162.63,'0.0[00000000000000]','3162.63'],                 [1.99,'0.[0]','2'],                 [1.0501,'0.00[0]','1.05'],                 [1.005,'0.00','1.01'],                 // leading zero                 [0, '00.0', '00.0'],                 [0.23, '000.[00]', '000.23'],                 [4, '000', '004'],                 [10, '00000', '00010'],                 [1000, '000,0', '1,000'],                 [1000, '00000,0', '01,000'],                 [1000, '0000000,0', '0,001,000'],                 // abbreviations                 [2000000000,'0.0a','2.0b'],                 [1230974,'0.0a','1.2m'],                 [1460,'0a','1k'],                 [-104000,'0 a','-104 k'],                 [999950,'0.0a','1.0m'],                 [999999999,'0a','1b'],                 // forced abbreviations                 [-5444333222111, '0,0 ak', '-5,444,333,222 k'],                 [5444333222111, '0,0 am', '5,444,333 m'],                 [-5444333222111, '0,0 ab', '-5,444 b'],                 [-5444333222111, '0,0 at', '-5 t'],                 [123456, '0.0[0] ak', '123.46 k'],                 [150,'0.0 ak','0.2 k']             ],             i,             n,             output;          for (i = 0; i < tests.length; i++) {             n = numeral(tests[i][0]);             output = n.format(tests[i][1]);              expect(output).to.equal(tests[i][2]);              expect(typeof output).to.equal('string');         }     }); }); 

字节转换

比如将 1024 转为 1KB,将 1024*1024 转为 1MB。将请看示例:

PS D:spug-study> node  Welcome to Node.js v16.14.2. Type ".help" for more information. > let numeral = require('numeral') undefined > numeral(1024).format('0b') '1KB' > numeral(1024*1024).format('0b') '1MB' > numeral(1024*1024*1024).format('0b') '1GB' > numeral(1024*1024*1024*1024).format('0b') '1TB' > numeral(1024*1024*1024*1024*32).format('0b') '35TB' > 

Tip:笔者直接在 node 环境下运行。更多格式化语法请看 bytes.js 文件。

// node_modulesnumeraltestsformatsbytes.js it('should format to bytes', function() {     var decimal = 1000;     var binary = 1024;     var tests = [             [0,'0b','0B'],             [null,'0 b','0 B'],             [100,'0b','100B'],             [binary * 2,'0 ib','2 KiB'],             [Math.pow(binary, 2) * 5,'0ib','5MiB'],             [Math.pow(binary, 3) * 7.343,'0.[0] ib','7.3 GiB'],             [Math.pow(binary, 4) * 3.1536544,'0.000ib','3.154TiB'],             [Math.pow(binary, 5) * 2.953454534534,'0ib','3PiB'],             [decimal * 2,'0 b','2 KB'],             [Math.pow(decimal, 2) * 5,'0b','5MB'],             [Math.pow(decimal, 3) * 7.343,'0.[0] b','7.3 GB'],             [Math.pow(decimal, 4) * 3.1536544,'0.000b','3.154TB'],             [Math.pow(decimal, 5) * 2.953454534534,'0b','3PB']         ],         i;      for (i = 0; i < tests.length; i++) {         expect(numeral(tests[i][0]).format(tests[i][1])).to.equal(tests[i][2]);     } }); 
字节转数字

比如可以将 1KB 转为数字,但结果只是 1000,如果要 1024,需要使用 1 KiB。请看示例:

> numeral('1KB').value() 1000 > numeral('1 KiB').value() 1024 > numeral('1MB').value() 1000000 

Tip:有关字节反解析的更多介绍请看 bytes.js

// node_modulesnumeraltestsformatsbytes.js it('should unformat to number', function() {     var decimal = 1000;     var binary = 1024;     var tests = [             ['0B', 0],             ['0 B', 0],             ['100B', 100],             ['2 KiB', binary * 2],             ['5MiB', Math.pow(binary, 2) * 5],             ['7.3 GiB', Math.pow(binary, 3) * 7.3],             ['3.154TiB', Math.pow(binary, 4) * 3.154],             ['3PiB', Math.pow(binary, 5) * 3],             ['2 KB', decimal * 2],             ['5MB', Math.pow(decimal, 2) * 5],             ['7.3 GB', Math.pow(decimal, 3) * 7.3],             ['3.154TB', Math.pow(decimal, 4) * 3.154],             ['3PB', Math.pow(decimal, 5) * 3]         ],         i;      for (i = 0; i < tests.length; i++) {         expect(numeral(tests[i][0]).value()).to.equal(tests[i][1]);     } }); 

时间转换转化

将数字(秒)转为时间形式。请看示例:

> numeral(1).format('00:00:00') '0:00:01' > numeral(60).format('00:00:00') '0:01:00' > numeral(60*60).format('00:00:00') '1:00:00' 

百分比转化

请看示例:

> numeral(0.974878234).format('0.000%') '97.488%' > numeral(0).format('0%') '0%' > numeral(1).format('0%') '100%' 

Tip:更多介绍请看 node_modulesnumeraltestsformatspercentage.js

货币转化

请看示例:

> numeral(1000.234).format('$0,0.00') '$1,000.23' 

Tip:更多用法请看 currency.js

// node_modulesnumeraltestsformatscurrency.js describe('Currency', function() {     after(function() {         numeral.reset();     });      it('should format to currency', function() {         var tests = [                 [0,'$0.00','$0.00'],                 [null,'$0.00','$0.00'],                 [0.99,'$0,0.00','$0.99'],                 [1000.234,'$0,0.00','$1,000.23'],                 [1001,'$ 0,0.[00]','$ 1,001'],                 [1000.234,'0,0.00 $','1,000.23 $'],                 [-1000.234,'0,0.00 $','-1,000.23 $'],                 [-1000.234,'($0,0)','($1,000)'],                 [-1000.234,'(0,0$)','(1,000$)'],                 [-1000.234,'(0,0 $)','(1,000 $)'],                 [-1000.234,'$0.00','-$1000.23'],                 [-1000.234,'$ 0.00','-$ 1000.23'],                 [1230974,'($0.00 a)','$1.23 m'],                 [-1000.234,'$ (0,0)','$ (1,000)'],                 [-1000.234,'$(0,0)','$(1,000)'],                 [-1000.234,'$ (0,0.00)','$ (1,000.23)'],                 [-1000.234,'$(0,0.00)','$(1,000.23)'],                 [-1000.238,'$(0,0.00)','$(1,000.24)'],                 [-1000.234,'$-0,0','$-1,000'],                 [-1000.234,'$ -0,0','$ -1,000'],                 [1000.234,'$ (0,0)','$ 1,000'],                 [1000.234,'$(0,0)','$1,000'],                 [1000.234,'$ (0,0.00)','$ 1,000.23'],                 [1000.234,'$(0,0.00)','$1,000.23'],                 [1000.238,'$(0,0.00)','$1,000.24'],                 [1000.234,'$-0,0','$1,000'],                 [1000.234,'$ -0,0','$ 1,000']             ],             i;          for (i = 0; i < tests.length; i++) {             expect(numeral(tests[i][0]).format(tests[i][1])).to.equal(tests[i][2]);         }     });      it('should unformat to currency', function() {         var tests = [                 ['$0.00', 0],                 ['$0.99', 0.99],                 ['$1,000.23', 1000.23],                 ['1,000.23 $', 1000.23],                 ['($1,000)', -1000],                 ['-1,000$', -1000],                 ['$1.23 m', 1230000],             ],             i;          for (i = 0; i < tests.length; i++) {             expect(numeral(tests[i][0]).value()).to.equal(tests[i][1]);         }     }); }); 

指数转化

请看示例:

> numeral(77777777.1234).format('0.0e+0') '7.8e+7' 

Tip:更多用法请看 exponential.js

// node_modulesnumeraltestsformatsexponential.js it('should format to exponential notation', function() {     var tests = [             [0,'0e+0','0e+0'],             [null,'0e+0','0e+0'],             [1,'0e+0','1e+0'],             [77.1234,'0.0e+0','7.7e+1'],             [0.000000771234,'0.0e-0','7.7e-7'],             [-0.000000771234,'0.00e-0','-7.71e-7'],             [77.1234,'0.000e+0','7.712e+1'],             [-1000830298,'0.0[000]e+0','-1.0008e+9']         ],         i;      for (i = 0; i < tests.length; i++) {         expect(numeral(tests[i][0]).format(tests[i][1])).to.equal(tests[i][2]);     } }); 

比特率转化

比特率,是指单位时间内传送的比特(bit)数,单位为bps(bit per second)。

> numeral(.0056).format('0 BPS') '56 BPS' 

Tip:更多用法请看 bps.js

// node_modulesnumeraltestsformatsbps.js it('should format to bps', function() {     var tests = [             [0,'0 BPS','0 BPS'],             [0.0001, '0 BPS', '1 BPS'],             [.0056, '0 BPS', '56 BPS'],             [.25, '0BPS', '2500BPS'],             [.000001, '0.00 BPS', '0.01 BPS']         ],         i;      for (i = 0; i < tests.length; i++) {         expect(numeral(tests[i][0]).format(tests[i][1])).to.equal(tests[i][2]);     } }); 

四则运算

numeral 提供加减乘除四则运算的方法,例如 100010 等于 1010。请看示例:

> numeral(1000).add(10).value() 1010 

Tip:更多介绍请看 numeral.js

// node_modulesnumeraltestsnumeral.js describe('Manipulate', function() {     // 加法     describe('Add', function() {         it('should add', function() {             var tests = [                     [1000,10,1010],                     [0.5,3,3.5],                     [-100,200,100],                     [0.1,0.2,0.3],                     [0.28,0.01,0.29],                     [0.289999,0.000001,0.29],                     [0.29,0.01,0.3]                 ],                 num;              for (var i = 0; i < tests.length; i++) {                 num = numeral(tests[i][0]);                  num.add(tests[i][1]);                  expect(num.value()).to.equal(tests[i][2]);             }         });     });      // 减法     describe('Subtract', function() {         it('should subtract', function() {             var tests = [                     [1000,10,990],                     [0.5,3,-2.5],                     [-100,200,-300],                     [0.3,0.1,0.2],                     [0.28,0.01,0.27],                     [0.29,0.01,0.28]                 ],                 num;              for (var i = 0; i < tests.length; i++) {                 num = numeral(tests[i][0]);                  num.subtract(tests[i][1]);                  expect(num.value()).to.equal(tests[i][2]);             }         });     });      // 乘法     describe('Multiply', function() {         it('should multiply', function() {             var tests = [                     [1000,10,10000],                     [0.5,3,1.5],                     [-100,200,-20000],                     [0.1,0.2,0.02],                     [0.28,0.01,0.0028],                     [0.29,0.01,0.0029],                     [0.00000231,10000000,23.1]                 ],                 num;              for (var i = 0; i < tests.length; i++) {                 num = numeral(tests[i][0]);                  num.multiply(tests[i][1]);                  expect(num.value()).to.equal(tests[i][2]);             }         });     });      // 除法     describe('Divide', function() {         it('should divide', function() {             var tests = [                     [1000,10,100],                     [0.5,3,0.16666666666666666],                     [-100,200,-0.5],                     [5.3,0.1,53],                     [0.28,0.01,28],                     [0.29,0.01,29]                 ],                 num;              for (var i = 0; i < tests.length; i++) {                 num = numeral(tests[i][0]);                  num.divide(tests[i][1]);                  expect(num.value()).to.equal(tests[i][2]);             }         });     });      // 差值。例如 1000 和 10 相差 990。     describe('Difference', function() {         it('should find a difference', function() {             var tests = [                 [1000,10,990],                 [0.5,3,2.5],                 [-100,200,300],                 [0.3,0.2,0.1],                 [0.28,0.01,0.27],                 [0.29,0.01,0.28]             ],             num;              for (var i = 0; i < tests.length; i++) {                 num = numeral(tests[i][0]);                  expect(num.difference(tests[i][1])).to.equal(tests[i][2]);             }         });     });      // 四舍五入。     describe('Rounding', function() {         it('should format with rounding', function() {             var tests = [                     // value, format string, expected w/ floor, expected w/ ceil                     [2280002, '0.00a', '2.28m', '2.29m'],                     [10000.23,'0,0','10,000', '10,001'],                     [1000.234,'0,0.00','1,000.23', '1,000.24'],                     [0.97487823,'0.000','0.974','0.975'],                     [-0.433,'0.0','-0.5', '-0.4']                 ],                 i;              for (i = 0; i < tests.length; i++) {                 // floor                 expect(numeral(tests[i][0]).format(tests[i][1], Math.floor)).to.equal(tests[i][2]);                  // ceil                 expect(numeral(tests[i][0]).format(tests[i][1], Math.ceil)).to.equal(tests[i][3]);             }         });     }); }); 

多语言

需求:数字很长时,由于排版的考虑,需要将数字显示的更短,转为指数勉强可以,但对很多人还是不友好,如果能转为 123.5百万 这种形式就完美了。

numeral 提供了缩写,比如可以将 1230974 转为 1.2m(m,指百万):

// node_modulesnumeraltestsnumeral.js ... // abbreviations [2000000000,'0.0a','2.0b'], [1230974,'0.0a','1.2m'], [1460,'0a','1k'], [-104000,'0 a','-104 k'], [999950,'0.0a','1.0m'], [999999999,'0a','1b'], 

请看示例:

const numeral = require('numeral'); var number5 = numeral(123456789).format('0.0a') // 123.5m console.log('number5: ', number5); 

123.5m 是多少,能否转为中文?笔者在 chs.js 中找到如下代码:

// node_modulesnumerallocaleschs.js  numeral.register('locale', 'chs', {     delimiters: {         thousands: ',',         decimal: '.'     },     abbreviations: {         thousand: '千',         million: '百万',         billion: '十亿',         trillion: '兆'     },     ordinal: function (number) {         return '.';     },     currency: {         symbol: '¥'     } }); 

通过引入 chs 并切换成中文,成功将 123456789 转为 123.5百万。请看示例:

const numeral = require('numeral'); // 加载中文 + require('numeral/locales/chs') // 切换成中文 + numeral.locale('chs') const number5 = numeral(123456789).format('0.0a') // number5:  123.5百万 console.log('number5: ', number5); 

Tip:对于单页面项目,在其他组件中若需要使用英文,比如不要 123.5百万,而要 123.5m,直接切换语言(numeral.locale('en'))即可。就像这样:

... const number5 = numeral(123456789).format('0.0a') // number5:  123.5百万 console.log('number5: ', number5);  + numeral.locale('en') const number6 = numeral(123456789).format('0.0a')  // number6:  123.5m console.log('number6: ', number6); 

笔者的示例

import React from 'react'; const numeral = require('numeral'); require('numeral/locales/chs') numeral.locale('chs')  function Test() {   const number = numeral(1000).format('0,0');   // number:  1,000   console.log('number: ', number);   const number2 = numeral(123456789).format('0,0');   // number2:  123,456,789   console.log('number2: ', number2);   // 四舍五入   const number3 = numeral(1.93).format('0,0');   // number3:  2   console.log('number3: ', number3);   // 四舍五入   const number4 = numeral(1.23).format('0,0');   // number4:  1   console.log('number4: ', number4);      const number5 = numeral(123456789).format('0.0a')   // number5:  123.5百万   console.log('number5: ', number5);    numeral.locale('en')   const number6 = numeral(123456789).format('0.0a')      // number6:  123.5m   console.log('number6: ', number6);   return (     <div>       react 项目     </div>   ) }  export default Test 

发表评论

评论已关闭。

相关文章