如何在NodeJS中使用Map将具有相同属性值的对象分组?

时间:2020-10-23 15:04:15

标签: javascript node.js arrays dictionary collections

这三个JSON数组具有类型123的错误详细信息,如下所示

const data1 =
[
  {
    "ErrorType": "Error-1A",
    "Error": "wrong ip address for 1A",
    "SERVER_COUNT": 7
  },
  {
    "ErrorType": "Error-1B",
    "Error": "password incorrect for 1B",
    "SERVER_COUNT": 6
  },

];

const data2 = 
[
  {
    "ErrorType": "Error-2A",
    "Error": "wrong data for 2A",
    "SERVER_COUNT": 8
  },
  {
    "ErrorType": "Error-2B",
    "Error": "password incorrect for 2B",
    "SERVER_COUNT": 3
  },

];

const data3 = 
[
  {
    "ErrorType": "Error-3A",
    "Error": "wrong data for 3A",
    "SERVER_COUNT": 1
  },
  {
    "ErrorType": "Error-3B",
    "Error": "password incorrect for 3C",
    "SERVER_COUNT": 5
  },

];

我想结合3个JSON数组data1,data2,data3,最后的JSON对象应如下所示:

{
  "details1": {
   "7": {
    "ErrorType": "Error-1A",
    "Error": "wrong ip address for 1A"
   },
      "6": {
    "ErrorType": "Error-1B",
    "Error": "password incorrect for 1B"
   }
},
  "details2": {
   "8": {
    "ErrorType": "Error-2A",
    "Error": "wrong ip address for 2A"
   },
      "3": {
    "ErrorType": "Error-2B",
    "Error": "password incorrect for 2B"
   }
},
  "details3": {
      "5": {
    "ErrorType": "Error-3B",
    "Error": "password incorrect for 3B"
   },
   "1": {
    "ErrorType": "Error-3A",
    "Error": "wrong ip address for 3A"
   }
}
}

请注意,Error-1AError-1B的计数相同。任何两种错误类型可以具有相同的计数。 我正在使用以下函数循环遍历数组元素,并使用SERVER_COUNT属性作为键将每个元素转换为对象属性。

let finalData = {
  details1: dataToDetails(data1),
  details2: dataToDetails(data2),
  details3: dataToDetails(data3)
};

function dataToDetails (data) {
  let result = {};
  data.forEach(({
                  ErrorType,
                  Error,
                  SERVER_COUNT
              }) => result[SERVER_COUNT] = result[SERVER_COUNT] ? [...result[SERVER_COUNT], {
    ErrorType,
    Error
}] : [{
    ErrorType,
    Error
}]);
  return result;
}

上面的代码给出正确的结果。唯一的问题是SERVER_COUNT的顺序不是相反的。 如何修改上述功能,以使对于每种类型1 2 3,我都会得到SERVER_COUNT,其最高值首先显示?

Current output:

{
  "details1": {
   "6": {
    "ErrorType": "Error-1A",
    "Error": "wrong ip address for 1A"
   },
      "7": {
    "ErrorType": "Error-1B",
    "Error": "password incorrect for 1B"
   }
},
  "details2": {
      "3": {
    "ErrorType": "Error-2B",
    "Error": "password incorrect for 2B"
   },
   "8": {
    "ErrorType": "Error-2A",
    "Error": "wrong ip address for 2A"
   }
},
  "details3": {
   "1": {
    "ErrorType": "Error-3A",
    "Error": "wrong ip address for 3A"
   },
      "5": {
    "ErrorType": "Error-3B",
    "Error": "password incorrect for 3B"
   }
}
}

Desired output

{
  "details1": {
   "7": {
    "ErrorType": "Error-1A",
    "Error": "wrong ip address for 1A"
   },
      "6": {
    "ErrorType": "Error-1B",
    "Error": "password incorrect for 1B"
   }
},
  "details2": {
   "8": {
    "ErrorType": "Error-2A",
    "Error": "wrong ip address for 2A"
   },
      "3": {
    "ErrorType": "Error-2B",
    "Error": "password incorrect for 2B"
   }
},
  "details3": {
      "5": {
    "ErrorType": "Error-3B",
    "Error": "password incorrect for 3B"
   },
   "1": {
    "ErrorType": "Error-3A",
    "Error": "wrong ip address for 3A"
   }
}
}

我正在尝试按以下方式使用Map,但它给出的是空值:

function dataToDetails(data) {
    let result = new Map();
    
    data.sort( ( { SERVER_COUNT: a }, { SERVER_COUNT: b } ) => b - a )

    data.forEach(
        ({ SERVER_COUNT, ...rest }) =>
            result.set(SERVER_COUNT, result.has(SERVER_COUNT)
                ? result.get(SERVER_COUNT).concat([rest])
                : [rest]),
    );
    return result;
}

0 个答案:

没有答案