You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用Ramda高效实现12小时制时间格式转换?

嘿,完全懂你这种感觉!刚上手函数式和Ramda的时候,很容易把简单问题拆得太碎,导致代码反而比命令式复杂。我来分享几个更简洁、更符合Ramda风格的实现方式,同时保持可读性:

方案一:紧凑的管道式实现

这个版本用Ramda的核心管道函数pipe串联逻辑,同时结合少量箭头函数让代码更直观:

const formatTime = R.pipe(
  // 拆分时间为小时和分钟数组
  R.split(':'),
  // 调整小时部分为12小时制
  R.adjust(0, hrStr => {
    const hr = parseInt(hrStr, 10);
    // 处理0点(转12)、12点以上(减12)、其他保持原样
    return hr === 0 ? 12 : hr > 12 ? hr - 12 : hr;
  }),
  // 把数组转为参数,拼接成最终字符串
  R.apply((hr, min) => `${hr}:${min} ${parseInt(hr, 10) >= 12 ? 'PM' : 'AM'}`)
);

// 测试用例
formatTime('13:22'); // "1:22 PM"
formatTime('00:30'); // "12:30 AM"
formatTime('12:00'); // "12:00 PM"

方案二:纯Ramda函数组合(更函数式)

如果想尽量用Ramda的内置函数减少手动逻辑,可以把拆分逻辑成更小的纯函数,再组合起来:

// 把24小时制小时转为12小时制
const to12Hr = R.pipe(
  parseInt,
  R.cond([
    [R.equals(0), R.always(12)],   // 0点转12
    [R.gt(R.__, 12), R.subtract(R.__, 12)], // 大于12减12
    [R.T, R.identity] // 其他情况保持原样
  ])
);

// 获取上午/下午标识
const getMeridiem = R.pipe(
  parseInt,
  R.ifElse(R.gte(R.__, 12), R.always('PM'), R.always('AM'))
);

// 主格式化函数
const formatTime = R.pipe(
  R.split(':'),
  // 同时提取处理后的小时、原始分钟、上午/下午标识
  R.juxt([
    R.pipe(R.head, to12Hr, String),
    R.nth(1),
    R.pipe(R.head, getMeridiem)
  ]),
  // 拼接成最终字符串
  R.apply((hr, min, meridiem) => `${hr}:${min} ${meridiem}`)
);

// 测试用例
formatTime('13:22'); // "1:22 PM"
formatTime('09:45'); // "9:45 AM"
formatTime('24:00'); // "12:00 PM"(如果需要24点转12AM,可调整to12Hr的cond)

对你原有代码的小优化提示

  • 你用R.identity('AM')其实没必要,R.always('AM')才是返回固定字符串的正确方式(identity是返回输入参数,这里你并没有用到传入的x);
  • parseInt最好加上第二个参数10,避免遇到带前导零的字符串时自动解析为八进制;
  • 函数式编程不必追求“全Ramda函数”,适当结合箭头函数能让代码更易读,尤其是简单逻辑场景。

内容的提问来源于stack exchange,提问作者cdoshi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.07 13:07:35