如何合并多个多维JSON文件?

时间:2018-03-14 09:35:26

标签: javascript jquery arrays json object

我正在尝试将几个JSON对象合并为一个,但我很难搞清楚如何获得所需的结果。

我不擅长创建复杂的for循环,这阻止了我成功。

示例area1.json

        {
            data: [
                {
                    date: "2018031300",
                    p: [
                        {
                            lon: -5.555,
                            precip-intensity: 0,
                            wind-dir: 90.25001,
                            temperature: 3.7924042,
                            wind-speed: 8.692518,
                            weather-symbol: 3,
                            pressure-sealevel: 100247.5
                        },
                        {
                            lon: -4.444,
                            precip-intensity: 0,
                            wind-dir: 89.87501,
                            temperature: 3.1674042,
                            wind-speed: 8.731581,
                            weather-symbol: 3,
                            pressure-sealevel: 100238.5
                        }
                    ]
                },
                {
                    date: "2018031301",
                    p: [
                        {
                            lon: -5.555,
                            precip-intensity: 0.00390625,
                            wind-dir: 97.500015,
                            temperature: 3.6734467,
                            wind-speed: 8.874923,
                            weather-symbol: 3,
                            pressure-sealevel: 100265.625
                        },
                        {
                            lon: -4.444,
                            precip-intensity: 0.00390625,
                            wind-dir: 96.000015,
                            temperature: 3.1109467,
                            wind-speed: 9.066329,
                            weather-symbol: 3,
                            pressure-sealevel: 100260.625
                        }       
                    ]
                }
            ]
        }

示例area2.json

        {
            data: [
                {
                    date: "2018031300",
                    p: [
                        {
                            lon: -7.777,
                            precip-intensity: 0.0078125,
                            wind-dir: 96.25001,
                            temperature: 4.792404,
                            wind-speed: 10.200331,
                            weather-symbol: 3,
                            pressure-sealevel: 100237
                        },
                        {
                            lon: -6.666,
                            precip-intensity: 0,
                            wind-dir: 86.50001,
                            temperature: 4.167404,
                            wind-speed: 11.106581,
                            weather-symbol: 3,
                            pressure-sealevel: 100243
                        }
                        ]
                },
                {
                    date: "2018031301",
                    p: [
                        {
                            lon: -7.777,
                            precip-intensity: 0.03125,
                            wind-dir: 92.625015,
                            temperature: 4.7359467,
                            wind-speed: 11.066329,
                            weather-symbol: 3,
                            pressure-sealevel: 100242.125
                        },
                        {
                            lon: -6.666,
                            precip-intensity: 0.0078125,
                            wind-dir: 90.750015,
                            temperature: 4.2359467,
                            wind-speed: 11.24211,
                            weather-symbol: 3,
                            pressure-sealevel: 100269.625
                        }           
                        ]
                }
                ]
        }

这是理想的结果

结合area3.json

        {
            data: [
                {
                    date: "2018031300",
                    p: [
                        {
                            lon: -7.777,
                            precip-intensity: 0.0078125,
                            wind-dir: 96.25001,
                            temperature: 4.792404,
                            wind-speed: 10.200331,
                            weather-symbol: 3,
                            pressure-sealevel: 100237
                        },
                        {
                            lon: -6.666,
                            precip-intensity: 0,
                            wind-dir: 86.50001,
                            temperature: 4.167404,
                            wind-speed: 11.106581,
                            weather-symbol: 3,
                            pressure-sealevel: 100243
                        },
                        {
                            lon: -5.555,
                            precip-intensity: 0,
                            wind-dir: 90.25001,
                            temperature: 3.7924042,
                            wind-speed: 8.692518,
                            weather-symbol: 3,
                            pressure-sealevel: 100247.5
                        },
                        {
                            lon: -4.444,
                            precip-intensity: 0,
                            wind-dir: 89.87501,
                            temperature: 3.1674042,
                            wind-speed: 8.731581,
                            weather-symbol: 3,
                            pressure-sealevel: 100238.5
                        }
                    ]
                },
                {
                    date: "2018031301",
                    p: [
                        {
                            lon: -7.777,
                            precip-intensity: 0.03125,
                            wind-dir: 92.625015,
                            temperature: 4.7359467,
                            wind-speed: 11.066329,
                            weather-symbol: 3,
                            pressure-sealevel: 100242.125
                        },
                        {
                            lon: -6.666,
                            precip-intensity: 0.0078125,
                            wind-dir: 90.750015,
                            temperature: 4.2359467,
                            wind-speed: 11.24211,
                            weather-symbol: 3,
                            pressure-sealevel: 100269.625
                        },          
                        {
                            lon: -5.555,
                            precip-intensity: 0.00390625,
                            wind-dir: 97.500015,
                            temperature: 3.6734467,
                            wind-speed: 8.874923,
                            weather-symbol: 3,
                            pressure-sealevel: 100265.625
                        },
                        {
                            lon: -4.444,
                            precip-intensity: 0.00390625,
                            wind-dir: 96.000015,
                            temperature: 3.1109467,
                            wind-speed: 9.066329,
                            weather-symbol: 3,
                            pressure-sealevel: 100260.625
                        }       
                    ]
                }
            ]
        }

这个帖子的答案几乎就是...... Merge JSON Data by Key

我试过这段代码......

        function mergeJson(target) {
            for (var argi = 1; argi < arguments.length; argi++) {
                var source = arguments[argi];
                for (var key in source) {
                    if (!(key in target)) {
                        target[key] = [];
                    }
                    for (var i = 0; i < source[key].length; i++) {
                        target[key].push(source[key][i]);
                    }
                }
            }
            return target;
        }


        var finalJson = mergeJson({}, area1, area2);

这给了我两个阵列......

1 个答案:

答案 0 :(得分:3)

您复制粘贴了执行不同合并的代码段。给定的合并确实:

{ a: [1, 2] } + { a: [3] } = { a: [1, 2, 3] }

您的数据格式要求更复杂的合并:

{ data: [ { key: "a", values: [1, 2] } ] } + 
{ data: [ { key: "a", values: [3] } ] } =
{ data: [ { key: "a", values: [1, 2, 3] }

放开第一个街区的逻辑,你会得到:

 { data: [ { key: "a", values: [1, 2] },
           { key: "a", values: [3] } ] }

正如你所说,这不是你想要的。

此比较应明确指出您需要找到一种方法来收集类似key值的数据(格式为date),然后才能开始合并

这是一个示例实现,包括使用您提供的代码段时的预处理任务。代码在评论中解释。

var area1={data:[{date:"2018031300",p:[{lon:-5.555},{lon:-4.444}]},{date:"2018031301",p:[{lon:-5.555},{lon:-4.444}]}]},area2={data:[{date:"2018031300",p:[{lon:-7.777},{lon:-6.666}]},{date:"2018031301",p:[{lon:-7.777},{lon:-6.666}]}]};


const mergeAreas = (area1, area2) => {
  // Skip the part of the structure that's always the same:
  const vals1 = area1.data;
  const vals2 = area2.data;
  
  // to { [date]: points }
  const valObj1 = arrayToObject(x => x.date, x => x.p, vals1);
  const valObj2 = arrayToObject(x => x.date, x => x.p, vals2);
  
  // Merge using the strategy you provided:
  const mergedObj = mergeJson({}, valObj1, valObj2);
  
  // Go back to the original format: [ { date, p } ]
  const mergedData = objToArray(([date, p]) => ({ date, p }), mergedObj);
  
  // Wrap it back up in the base structure: { data: [ ] }
  return {
    data: mergedData
  }

};

// Takes an array of items and returns a single object.
// The items are stored in a key returned by `getKey`
// The items are represented by a value returned by `getValue`
// When `getKey` returns duplicates, it overwrites the previous entry
function arrayToObject(getKey, getValue, xs) {
  return xs.reduce(
    (acc, x) => Object.assign(acc, { [getKey(x)]: getValue(x) }),
    {}
  );
};

// This takes an object and returns an array based on its entries
function objToArray(kvpToItem, obj) {
  return Object.entries(obj).map(kvpToItem);
}

// Provided by OP from answer https://stackoverflow.com/a/16302909/3297291
function mergeJson(target) {
  for (var argi = 1; argi < arguments.length; argi++) {
    var source = arguments[argi];
    for (var key in source) {
      if (!(key in target)) {
        target[key] = [];
      }
      for (var i = 0; i < source[key].length; i++) {
        target[key].push(source[key][i]);
      }
    }
  }
  return target;
}

// Run with example data
var finalJson = mergeAreas(area1, area2);
console.log(finalJson);