【问题标题】:JSON.parse result to proper array of objectsJSON.parse 结果到正确的对象数组
【发布时间】:2019-10-22 17:38:56
【问题描述】:

在我的 JSON.parse 之后我有这个数据

 data = [
  {
      "serviceType": "service1",
      "method": "close",
      "quantity": 56
  },
  {
      "serviceType": "service1",
      "method": "divert",
      "quantity": 175
  },
  {
      "serviceType": "service1",
      "method": "reverted",
      "quantity": 80
  },
  {
      "serviceType": "service2",
      "method": "close",
      "quantity": 15
  },
  {
      "serviceType": "service2",
      "method": "divert",
      "quantity": 149
  },
  {
      "serviceType": "service2",
      "method": "reverted",
      "quantity": 149
  },
  {
      "serviceType": "service3",
      "method": "close",
      "quantity": 87
  },....
  }
]

我需要它像 data.json 来自这个 d3 example 其中 categorie 是我的 serviceType,它是每个对象的第一个属性(每个 serviceType 一个对象),然后是每个对象的第二个属性应该是带有方法和数量的对象数组。

我一直在为data 中的每个对象使用forEach,并且我正在推动每个serviceType OK(没有第二个属性)中的第一个。问题是我不知道如何update对象values(第二个属性)在正确的对象内(根据当前的serviceType)。

finalArray = [];
data.forEach(function (d, index) {
    var serviceType = d.serviceType;    
    const found = finalArray.some( el => el.serviceType === serviceType);
    if (!found) {
        var obj = createObj(d); //function returning an obj with the desired structure
        finalArray.push(obj);                
    }...
});

这是转换应该如何结束的示例。

[
    {
        "serviceType": "service1", 
        "values": [
            {
                "quantity": 0, 
                "method": "close"
            }, 
            {
                "quantity": 4, 
                "method": "divert"
            }, 
            {
                "quantity": 12, 
                "method": "reverted"
            }, 
            {
                "quantity": 0, 
                "method": "checked"
            }
        ]
    }, 
    {
        "serviceType": "service2", 
        "values": [
            {
                "quantity": 1, 
                "method": "close"
            }, 
            {
                "quantity": 21, 
                "method": "divert"
            }, 
            {
                "quantity": 13, 
                "method": "reverted"
            },  
            {
                "quantity": 6, 
                "method": "checked"
            }
        ]
    }, ...

【问题讨论】:

  • 你有想要的结果的例子吗?
  • @NinaScholz 我编辑了问题,谢谢。

标签: javascript json


【解决方案1】:

您可以使用Map 并将相同的serviceType 分组。稍后构建一个具有categorievalues 属性的数组。

var data = [{ serviceType: "service1", method: "close", quantity: 56 }, { serviceType: "service1", method: "divert", quantity: 175 }, { serviceType: "service1", method: "reverted", quantity: 80 }, { serviceType: "service2", method: "close", quantity: 15 }, { serviceType: "service2", method: "divert", quantity: 149 }, { serviceType: "service2", method: "reverted", quantity: 149 }, { serviceType: "service3", method: "close", quantity: 87 }],
    result = Array.from(
        data.reduce((m, { serviceType, ...o }) => m.set(serviceType, [...(m.get(serviceType) ||  []), o]), new Map),
        ([categorie, values]) => ({ categorie, values })
    );

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

【讨论】:

  • 整洁,我会深入研究以正确理解它,我不太精通Map。非常感谢。
【解决方案2】:

您可以使用reduce 方法获取一个具有分组服务的对象,然后从该对象中获取一组值。

const data = [{"serviceType":"service1","method":"close","quantity":56},{"serviceType":"service1","method":"divert","quantity":175},{"serviceType":"service1","method":"reverted","quantity":80},{"serviceType":"service2","method":"close","quantity":15},{"serviceType":"service2","method":"divert","quantity":149},{"serviceType":"service2","method":"reverted","quantity":149},{"serviceType":"service3","method":"close","quantity":87}]

const object = data.reduce((r, {serviceType: s, ...rest}) => {
  if(!r[s]) r[s] = {categorie:s, values: [rest]};
  else r[s].values.push(rest);
  return r;
}, {});

const result = Object.values(object);
console.log(result);

【讨论】:

    【解决方案3】:

    试试这个:

    const result = [...new Set(data.map(e => e.serviceType))].map(serviceType => {
      const re = { serviceType };
      re.values = data
        .filter(e => e.serviceType === serviceType)
        .map(v => ({ method: v.method, quantity: v.quantity }));
      return re;
    });
    

    首先我得到所有的 serviceTypes(使用 ...new Set() 的部分),然后我为每个对象创建一个包含 serviceType-name 和值的对象,我通过过滤掉不相关的对象并删除 serviceType-property相关的。

    【讨论】:

      【解决方案4】:
      data.reduce((acc, value) => {
          var {serviceType, method, quantity} = value;
          var foundExisting = acc.find(v => v.serviceType == serviceType);
      
          if(foundExisting){
              foundExisting.values.push({method, quantity})
          } else {
              acc.push({serviceType, values: [{method, quantity}]})
          }
      
          return acc;
      }, [])
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2019-10-29
        • 1970-01-01
        • 2011-07-22
        • 2019-05-29
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多