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

如何使用lodash以更简洁的函数式方式扁平化对象内的嵌套数组

我有如下 facebookResponseObject 对象,需要将其中值为数组类型的字段做扁平化处理。目前我使用reduce函数实现该需求,但想了解是否有更简洁的函数式写法可以解决这个问题。

输入示例

const facebookResponseObject = {
  account_currency: "xxx",
  campaign_name: "xxxxxxxx",
  account_name: "xxxxxxxx",
  adset_name: "xxxxxxxx",
  ad_name: "xxxxxxxx",
  reach: "xxxx",
  impressions: "xxxx",
  frequency: "xxxx",
  spend: "xxxx",
  cpm: "xxxx",
  inline_link_clicks: "xxxx",
  cost_per_inline_link_click: "xxxx",
  inline_link_click_ctr: "xxxx",
  clicks: "xxxx",
  cost_per_unique_click: "xxxx",
  cost_per_action_type: [
    { action_type: "link_click", value: "xxxx" },
    { action_type: "landing_page_view", value: "xxxx" },
    { action_type: "post_engagement", value: "xxxx" },
    { action_type: "page_engagement", value: "xxxx" },
    { action_type: "lead", value: "xxxx" },
    { action_type: "video_view", value: "xxxx" },
    { action_type: "like", value: "xxxx" },
  ],
  actions: [
    { action_type: "link_click", value: "xxxx" },
    { action_type: "landing_page_view", value: "xxxx" },
    { action_type: "post_engagement", value: "xxxx" },
    { action_type: "page_engagement", value: "xxxx" },
    { action_type: "post_reaction", value: "xxxx" },
    { action_type: "lead", value: "xxxx" },
    { action_type: "post", value: "xxxx" },
    { action_type: "comment", value: "xxxx" },
    { action_type: "video_view", value: "xxxx" },
    { action_type: "like", value: "xxxx" },
  ],
  test_key: [
    { action_type: "test1", value: "xxxx" },
    { action_type: "test2", value: "xxxx" },
    { action_type: "test3", value: "xxxx" },
    { action_type: "test4", value: "xxxx" },
  ],
  cpc: "xxxx",
  ctr: "xxxx",
  date_start: "xxxx-xx-xx",
  date_stop: "xxxx-xx-xx",
  account_id: "xxxxxxxx",
};

现有转换函数

const formatResponse = _.reduce(
  facebookResponseObject,
  (acc, cur, key) => {
    if (_.isArray(cur)) {
      acc = {
        ...acc,
        ..._.chain(cur)
          .keyBy(obj => `${key}.${obj.action_type}`)
          .mapValues(v => v.value)
          .value(),
      };
    } else {
      acc[key] = cur;
    }
    return acc;
  },
  {},
);

预期输出结果

{
  account_currency: 'xxx',
  campaign_name: 'xxxxxxxx',
  account_name: 'xxxxxxxx',
  adset_name: 'xxxxxxxx',
  ad_name: 'xxxxxxxx',
  reach: 'xxxx',
  impressions: 'xxxx',
  frequency: 'xxxx',
  spend: 'xxxx',
  cpm: 'xxxx',
  inline_link_clicks: 'xxxx',
  cost_per_inline_link_click: 'xxxx',
  inline_link_click_ctr: 'xxxx',
  clicks: 'xxxx',
  cost_per_unique_click: 'xxxx',
  'cost_per_action_type.link_click': 'xxxx',
  'cost_per_action_type.landing_page_view': 'xxxx',
  'cost_per_action_type.post_engagement': 'xxxx',
  'cost_per_action_type.page_engagement': 'xxxx',
  'cost_per_action_type.lead': 'xxxx',
  'cost_per_action_type.video_view': 'xxxx',
  'cost_per_action_type.like': 'xxxx',
  'actions.link_click': 'xxxx',
  'actions.landing_page_view': 'xxxx',
  'actions.post_engagement': 'xxxx',
  'actions.page_engagement': 'xxxx',
  'actions.post_reaction': 'xxxx',
  'actions.lead': 'xxxx',
  'actions.post': 'xxxx',
  'actions.comment': 'xxxx',
  'actions.video_view': 'xxxx',
  'actions.like': 'xxxx',
  'test_key.test1': 'xxxx',
  'test_key.test2': 'xxxx',
  'test_key.test3': 'xxxx',
  'test_key.test4': 'xxxx',
  cpc: 'xxxx',
  ctr: 'xxxx',
  date_start: 'xxxx-xx-xx',
  date_stop: 'xxxx-xx-xx',
  account_id: 'xxxxxxxx'
}

更精简的实现方案

1. 依赖Lodash的写法

逻辑拆分清晰,比原reduce写法少了分支判断和手动累加器维护:

const formatResponse = obj => ({
  // 保留所有非数组属性
  ..._.omitBy(obj, _.isArray),
  // 处理所有数组属性,拍平后合并
  ..._.chain(obj)
    .pickBy(_.isArray)
    .flatMap((arr, key) => arr.map(item => [`${key}.${item.action_type}`, item.value]))
    .fromPairs()
    .value()
})

2. 无依赖原生JS写法

不需要引入任何第三方库,兼容所有现代JS运行环境:

const formatResponse = obj => Object.fromEntries([
  // 保留非数组字段
  ...Object.entries(obj).filter(([_, val]) => !Array.isArray(val)),
  // 处理数组字段生成扁平化键值对
  ...Object.entries(obj)
    .filter(([_, val]) => Array.isArray(val))
    .flatMap(([key, arr]) => arr.map(item => [`${key}.${item.action_type}`, item.value]))
])

两种写法均为纯函数,输入输出与原实现完全一致,代码更加声明式,可读性更高。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.28 17:36:04