Skip to content

formatNumber

描述

数值格式化工具函数。将数值格式化为指定格式的字符串,支持多种格式化规则,包括基本数字格式化、万/亿单位转换、百分号格式化以及自定义格式化函数。

语法

ts
formatNumber(
  value: unknown,
  format: string | ((value: number) => string),
  fallback?: string
): string

参数

  • value (unknown): 需要格式化的值,支持数字、字符串、布尔值等类型
  • format (string | Function): 格式化规则
    • 字符串格式:支持 'M'、'W'、'Y'、'Amount'、'+M.N%' 等格式
    • 函数格式:自定义格式化函数,接收数字参数并返回字符串
  • fallback (string, 可选): 当输入值无效时的返回值,默认为 '--'

返回值

  • string: 格式化后的字符串

异常

  • TypeError: 当format参数为空或类型不正确时抛出

格式化规则

字符串格式

M格式(基本数字格式化)

  • M: 不保留小数,显示原始数值,如 123.456'123.456'
  • M.0: 保留0位小数(四舍五入),如 123.456'123'123.5'124'
  • M.1: 保留1位小数(四舍五入),如 123.456'123.5'123.44'123.4'
  • M.2: 保留2位小数(四舍五入),如 123.456'123.46'123.454'123.45'
  • M.3: 保留3位小数(四舍五入),如 123.456789'123.457'

W格式(万单位转换)

  • W: 转换为万单位(不保留小数),如 123456'12.3456万'
  • W.0: 转换为万单位(保留0位小数),如 123456'12万'
  • W.1: 转换为万单位(保留1位小数),如 123456'12.3万'
  • W.2: 转换为万单位(保留2位小数),如 123456'12.35万'
  • +W.2: 带正号的万单位,如 123456'+12.35万'

Y格式(亿单位转换)

  • Y: 转换为亿单位(不保留小数),如 1234567890'12.3456789亿'
  • Y.0: 转换为亿单位(保留0位小数),如 1234567890'12亿'
  • Y.1: 转换为亿单位(保留1位小数),如 1234567890'12.3亿'
  • Y.2: 转换为亿单位(保留2位小数),如 1234567890'12.35亿'
  • +Y.2: 带正号的亿单位,如 1234567890'+12.35亿'

Amount格式(自动单位判断)

  • Amount: 根据数值大小自动选择单位(不保留小数)
  • Amount.2: 根据数值大小自动选择单位(保留2位小数)
  • +Amount.2: 带正号的自动单位判断
  • 规则:
    • ≥1亿:使用亿单位,如 1234567890'12.35亿'
    • ≥1万:使用万单位,如 123456'12.35万'
    • <1万:保持原值,如 1234'1234'

百分号格式

  • M%: 转换为百分比(不保留小数),如 0.1234'12.34%'
  • M.2%: 转换为百分比,如 0.1234'12.34%'
  • +M.2%: 带正号的百分比,如 0.1234'+12.34%'
  • W.2%: 万单位+百分比,如 0.1234'12.34万%'
  • Y.2%: 亿单位+百分比,如 0.1234'12.34亿%'

自定义函数格式

传入自定义函数进行格式化,函数接收数字参数并返回字符串。

示例

基本格式化

ts
import { formatNumber } from '@fu/matrix';

// 不保留小数(显示原始值)
formatNumber(123.456, 'M'); // => '123.456'
formatNumber(123, 'M'); // => '123'
formatNumber(0, 'M'); // => '0'

// 保留小数位数(四舍五入)
formatNumber(123.456, 'M.2'); // => '123.46'
formatNumber(123.454, 'M.2'); // => '123.45'
formatNumber(123.456, 'M.0'); // => '123'
formatNumber(123.5, 'M.0'); // => '124'
formatNumber(123.456, 'M.3'); // => '123.456'

// 处理不同输入类型
formatNumber('123.456', 'M.2'); // => '123.46'
formatNumber(true, 'M.0'); // => '1'
formatNumber(false, 'M.0'); // => '0'

万单位格式化

ts
import { formatNumber } from '@fu/matrix';

// 不保留小数的万单位
formatNumber(123456, 'W'); // => '12.3456万'
formatNumber(10000, 'W'); // => '1万'
formatNumber(0, 'W'); // => '0万'

// 保留小数的万单位
formatNumber(123456, 'W.2'); // => '12.35万'
formatNumber(123456, 'W.1'); // => '12.3万'
formatNumber(123456, 'W.0'); // => '12万'

// 带正号的万单位
formatNumber(123456, '+W.2'); // => '+12.35万'
formatNumber(-123456, '+W.2'); // => '-12.35万'

亿单位格式化

ts
import { formatNumber } from '@fu/matrix';

// 不保留小数的亿单位
formatNumber(1234567890, 'Y'); // => '12.3456789亿'
formatNumber(100000000, 'Y'); // => '1亿'
formatNumber(0, 'Y'); // => '0亿'

// 保留小数的亿单位
formatNumber(1234567890, 'Y.2'); // => '12.35亿'
formatNumber(1234567890, 'Y.1'); // => '12.3亿'
formatNumber(1234567890, 'Y.0'); // => '12亿'

// 带正号的亿单位
formatNumber(1234567890, '+Y.2'); // => '+12.35亿'
formatNumber(-1234567890, '+Y.2'); // => '-12.35亿'

自动单位判断

ts
import { formatNumber } from '@fu/matrix';

// 自动选择单位
formatNumber(1234567890, 'Amount.2'); // => '12.35亿' (>=1亿,自动用亿)
formatNumber(123456, 'Amount.2'); // => '12.35万' (>=1万,自动用万)
formatNumber(1234, 'Amount.2'); // => '1234' (<1万,保持原值)
formatNumber(0, 'Amount.2'); // => '0' (<1万,保持原值)

// 带正号的自动单位判断
formatNumber(1234567890, '+Amount.2'); // => '+12.35亿'
formatNumber(123456, '+Amount.2'); // => '+12.35万'
formatNumber(1234, '+Amount.2'); // => '+1234'

百分号格式化

ts
import { formatNumber } from '@fu/matrix';

// 不保留小数的百分比
formatNumber(0.1234, 'M%'); // => '12.34%'
formatNumber(0.5, 'M%'); // => '50%'
formatNumber(1, 'M%'); // => '100%'

// 保留小数的百分比
formatNumber(0.1234, 'M.2%'); // => '12.34%'
formatNumber(0.5, 'M.2%'); // => '50.00%'
formatNumber(1, 'M.2%'); // => '100.00%'

// 带正号的百分比
formatNumber(0.1234, '+M.2%'); // => '+12.34%'
formatNumber(-0.1234, '+M.2%'); // => '-12.34%'

// 万单位+百分比
formatNumber(0.1234, 'W.2%'); // => '12.34万%'
formatNumber(0.5, 'W.2%'); // => '50.00万%'

// 亿单位+百分比
formatNumber(0.1234, 'Y.2%'); // => '12.34亿%'
formatNumber(0.5, 'Y.2%'); // => '50.00亿%'

自定义函数

ts
import { formatNumber } from '@fu/matrix';

// 货币格式化
const currencyFormat = (value: number) => `$${value.toFixed(2)}`;
formatNumber(123.456, currencyFormat); // => '$123.46'

// 自定义百分比
const customPercent = (value: number) => `${(value * 100).toFixed(1)}%`;
formatNumber(0.123, customPercent); // => '12.3%'

// 人民币格式化
const rmbFormat = (value: number) => `¥${value.toFixed(2)}`;
formatNumber(123.456, rmbFormat); // => '¥123.46'

无效值处理

ts
import { formatNumber } from '@fu/matrix';

// 默认fallback
formatNumber(null, 'M.2'); // => '--'
formatNumber(undefined, 'M.2'); // => '--'
formatNumber('', 'M.2'); // => '--'
formatNumber('invalid', 'M.2'); // => '--'
formatNumber(NaN, 'M.2'); // => '--'

// 自定义fallback
formatNumber(null, 'M.2', 'N/A'); // => 'N/A'
formatNumber('invalid', 'M.2', '错误'); // => '错误'

实际应用场景

ts
import { formatNumber } from '@fu/matrix';

// 股票价格显示
const stockPrice = 123.456;
formatNumber(stockPrice, 'M.2'); // => '123.46'
formatNumber(stockPrice, 'M'); // => '123.456'

// 涨跌幅显示
const changeRate = 0.1234;
formatNumber(changeRate, '+M.2%'); // => '+12.34%'
formatNumber(changeRate, 'M%'); // => '12.34%'

// 交易量显示(万单位)
const volume = 1234567;
formatNumber(volume, 'W.2'); // => '123.46万'
formatNumber(volume, '+W.2'); // => '+123.46万'

// 市值显示(亿单位)
const marketCap = 12345678900;
formatNumber(marketCap, 'Y.2'); // => '123.46亿'
formatNumber(marketCap, '+Y.2'); // => '+123.46亿'

// 自动单位判断(根据数值大小)
const smallValue = 1234;
const mediumValue = 123456;
const largeValue = 1234567890;

formatNumber(smallValue, 'Amount.2'); // => '1234' (<1万,保持原值)
formatNumber(mediumValue, 'Amount.2'); // => '12.35万' (>=1万,用万)
formatNumber(largeValue, 'Amount.2'); // => '12.35亿' (>=1亿,用亿)

// 自定义货币格式
const price = 123.456;
const currencyFormatter = (value: number) => `¥${value.toFixed(2)}`;
formatNumber(price, currencyFormatter); // => '¥123.46'

特性

输入值支持

  • 数字类型: 直接支持
  • 字符串类型: 自动转换为数字
  • 布尔类型: true → 1, false → 0
  • 其他类型: 尝试转换为数字,失败则返回fallback

格式化规则

  • M格式: 基本数字格式化,支持不保留小数或指定小数位数(四舍五入)
  • W格式: 万单位转换,自动除以10000并添加"万"单位
  • Y格式: 亿单位转换,自动除以100000000并添加"亿"单位
  • Amount格式: 智能单位判断,根据数值大小自动选择万、亿或原值
  • 百分号格式: 自动乘以100并添加%符号(四舍五入)
  • 组合格式: 支持正号、单位、百分号的组合,如 +W.2%Y.1
  • 自定义函数: 完全自定义的格式化逻辑

错误处理

  • 参数验证: 严格的参数类型检查
  • 无效值处理: 支持自定义fallback值
  • 异常捕获: 自定义函数执行失败时返回fallback

性能优化

  • 类型检查: 快速失败,避免不必要的计算
  • 字符串解析: 高效的正则表达式解析
  • 内存管理: 避免创建不必要的中间对象

兼容性

  • 浏览器支持: ✅ 所有现代浏览器
  • Node.js 支持: ✅ 所有版本
  • TypeScript 支持: ✅ 完整类型定义

注意事项

  1. M格式不传小数位数时,显示原始数值,不进行精度处理
  2. 百分号格式会自动将数值乘以100
  3. 自定义函数执行失败时会返回fallback值
  4. 无效的格式字符串会返回fallback值
  5. Infinity和-Infinity会直接转换为字符串

相关方法

版本历史

  • v1.0.0: 初始版本,支持基本M格式和百分号格式
  • v1.1.0: 新增W格式(万单位)、Y格式(亿单位)、Amount格式(自动单位判断)和组合格式支持