将JSON对象重新映射为其他JSON结构。

4
我正在尝试重新映射以下按类别格式化的JSON结构,然后每个类别可以包含多个位置。位置包含经度/纬度和区域代码:
{
  "cat1":[
    {"location":{
      "latitude":51.38,
      "longitude":4.34,
      "code":"0873"}
    },
    {"location":{
      "latitude":52.65,
      "longitude":6.74,
      "code":"0109"}
    },
    {"location":{
      "latitude":51.48,
      "longitude":4.33,
      "code":"0748"}
    },
    {"location":{
      "latitude":51.48,
      "longitude":4.33,
      "code":"0109"}
    }
  ],
  "cat2":[
    {"location":{
      "latitude":52.33,
      "longitude":4.32,
      "code":"0873"}
    },
    {"location":{
      "latitude":52.65,
      "longitude":6.74,
      "code":"0109"}
    },
    {"location":{
      "latitude":51.48,
      "longitude":4.33,
      "code":"0728"}
    }
  ],
  "cat3":[
    {"location":{
      "latitude":52.33,
      "longitude":4.32,
      "code":"0873"}
    },
    {"location":{
      "latitude":52.65,
      "longitude":6.74,
      "code":"0109"}
    },
    {"location":{
      "latitude":51.48,
      "longitude":4.33,
      "code":"0758"}
    }
  ]
}

在以下结构中,主要集中在区号上,然后将类别与其中实际位置联系起来。
{
  "code":[
    {"0873":[
      {"cat1":[
        {"location":{"latitude":51.38,"longitude":4.34}}
      ]},
      {"cat2":[
        {"location":{"latitude":52.33,"longitude":4.32}}
      ]},
      {"cat3":[
        {"location":{"latitude":52.33,"longitude":4.32}}
      ]}
    ]},

    {"0109":[
      {"cat1":[
        {"location":{"latitude":52.65,"longitude":6.74}},
        {"location":{"latitude":51.48,"longitude":4.33}}
      ]},
      {"cat2":[
        {"location":{"latitude":52.65,"longitude":6.74}}
      ]},
      {"cat3":[
        {"location":{"latitude":52.65,"longitude":6.74}}
      ]}

    ]},
    {"0748":[
      {"cat1":[
        {"location":{"latitude":51.48,"longitude":4.33}}
      ]}
    ]},

    {"0728":[
      {"cat2":[
        {"location":{"latitude":51.48,"longitude":4.33}}
      ]}
    ]},
    {"0758":[
      {"cat3":[
        {"location":{"latitude":51.48,"longitude":4.33}}
      ]}
    ]}

  ]
}

我尝试使用Javascript/Node完成这个任务,希望找到一种比手动遍历所有对象并重构它们更优雅的方法。我研究了reorientobstruction,但无法找到完成它的方法...
非常感谢您的帮助!
我知道上面的部分是从文件中读取并解析为对象的JSON字符串。
我目前的代码还没有完成,因为我不知道最好的方式是什么来执行remapJson()函数:
var fs = require('fs'),
jsonfile = require('jsonfile');

function remapJson(oldData) {
  var newData = {};

  // Do the convertion (loop all keys and values?)


  return newData
}

obj = jsonfile.readFileSync('oldstructure.json');

jsonfile.writeFileSync('newstructure.json', remapJson(obj));

2
你可以添加你的代码。请看这里:[mcve] - Nina Scholz
我可以建议使用javascript linq - asdf_enel_hak
请查看此链接:http://benalman.com/news/2010/03/theres-no-such-thing-as-a-json/ - user663031
我添加了一些代码并解释了一下,我首先将JSON字符串解析为一个对象。 - Max
2个回答

3
您可以使用迭代和递归的方法来处理哈希表中结果数组的问题。

var data = { cat1: [{ location: { latitude: 51.38, longitude: 4.34, code: "0873" } }, { location: { latitude: 52.65, longitude: 6.74, code: "0109" } }, { location: { latitude: 51.48, longitude: 4.33, code: "0748" } }, { location: { latitude: 51.48, longitude: 4.33, code: "0109" } }], cat2: [{ location: { latitude: 52.33, longitude: 4.32, code: "0873" } }, { location: { latitude: 52.65, longitude: 6.74, code: "0109" } }, { location: { latitude: 51.48, longitude: 4.33, code: "0728" } }], cat3: [{ location: { latitude: 52.33, longitude: 4.32, code: "0873" } }, { location: { latitude: 52.65, longitude: 6.74, code: "0109" } }, { location: { latitude: 51.48, longitude: 4.33, code: "0758" } }] },
    result = { code: [] };

Object.keys(data).forEach(function (key) {
    data[key].forEach(function (a) {
        [a.location.code, key].reduce(function (r, k) {
            var o = {};
            if (!r[k]) {
                r[k] = { _: [] };
                o[k] = r[k]._;
                r._.push(o);
            }
            return r[k];
        }, this)._.push({ location: { latitude: a.location.latitude, longitude: a.location.longitude } });
    }, this);
}, { _: result.code });

console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }


在代码片段上,它确实完美无缺。谢谢! 但是,在导入JSON文件并解析它时,它会出现错误: data[key].forEach(function (a) { ^ TypeError: data[key].forEach is not a function at Object.keys.forEach._ (/Users/mwesten/source/tekenradar/temp.js:30:17) at Array.forEach (native) 用于导入的文件 - Max
1
@Max,你可以先用Array.isArray(data[key])检查data[key]是否为数组。 - Nina Scholz
谢谢 ;) 它解决了问题! - Max
似乎仍然缺失很多...原始的JSON文件大小为473KB,而结果JSON文件大小为84KB,尽管结构并没有改变太多...我将尝试计算我缺失了多少,但我认为数组检查会过早地中断循环。上面发布的JSON是格式良好的,所以那不是问题... - Max

0

试一下这个

var a = //your json
var newArray = [];
for(var i in a){
    var obj = {};
    var newobj = {};
    var innerobj = {};
    var locationobj = {};
    if(a[i].length != 0){
        var keyname = i;
        for(var j = 0;j<a[i].length ; j++){
            if(a[i][j].location.code == "0873"){
                locationobj["latitude"] = a[i][j].location.latitude;
                locationobj["longitude"] = a[i][j].location.longitude;
                innerobj[i] = {"loaction":locationobj};
                obj[a[i][j].location.code] = innerobj;
                newArray.push({"code":obj})
            }else if(a[i][j].location.code == "0758"){
                locationobj["latitude"] = a[i][j].location.latitude;
                locationobj["longitude"] = a[i][j].location.longitude;
                innerobj[i] = {"loaction":locationobj};
                obj[a[i][j].location.code] = innerobj;
                newArray.push({"code":obj})
            }else if(a[i][j].location.code == "0109"){
                locationobj["latitude"] = a[i][j].location.latitude;
                locationobj["longitude"] = a[i][j].location.longitude;
                innerobj[i] = {"loaction":locationobj};
                obj[a[i][j].location.code] = innerobj;
                newArray.push({"code":obj})
            }

        }
    }
}

console.log(newArray)

你能提供一个不硬编码区号的版本吗? - user663031
这可能会很困难,因为代码位于循环内部,要获取它,您必须进行迭代... - Akshay
嗯,区域代码是动态的(它们是通过将位置数据(lon/lat)与包含写入该位置的区域代码的topoJSON文件进行匹配来找到的)。之后,我需要重新排序这些内容,以便能够创建该数据的Choropleth,因此我事先不知道区域代码.... - Max
将所有代码放入数组中,然后进行迭代会有奇效。 - Akshay

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接