Сортировка после группировки объектов в Javascript - PullRequest
0 голосов
/ 02 апреля 2020

Допустим, у меня есть следующие данные:

const collection = [
        {
            callId: "1",
            deadline: null
        },
        {
            callId: "1",
            deadline: null
        },
        {
            callId: "3",
            deadline: "2020-04-02T13:37:00.000Z" //assume its a JS date object
        },
        {
            callId: "3",
            deadline: "2020-04-06T08:33:00.000Z" //assume its a JS date object
        },
        {
            callId: "2",
            deadline: null
        },
        {
            callId: "2",
            deadline: "2020-04-06T08:33:00.000Z" //assume its a JS date object
        },
    ]

Я бы хотел сгруппировать их по callId, но сгруппированные данные отсортированы по deadline. Итак, я хочу получить результат:

const sorted = {
        "3": [
            {
                callId: "3",
                deadline: "2020-04-02T13:37:00.000Z"
            },
            {
                callId: "3",
                deadline: "2020-04-06T08:33:00.000Z"
            },
        ],
        "2": [
            {
                callId: "2",
                deadline: "2020-04-06T08:33:00.000Z"
            },
            {
                callId: "2",
                deadline: null
            },
        ],
        "1": [
            {
                callId: "1",
                deadline: null
            },
            {
                callId: "1",
                deadline: null
            },
        ],
    }

Я пытался использовать lodash:

const groupedData = _groupBy(collection, 'callId')
const sortedData = _sortBy(groupedData, [function (resultItem) {
        return _map(resultItem, function (value) {
            return value.deadline == null;
        });
    }]);

Но мне не удалось получить правильный результат:

[
[
    {
        "callId": "3",
        "deadline": "2020-04-02T13:37:00.000Z"
    },
    {
        "callId": "3",
        "deadline": "2020-04-06T08:33:00.000Z"
    }
],
[
    {
        "callId": "2",
        "deadline": null
    },
    {
        "callId": "2",
        "deadline": "2020-04-06T08:33:00.000Z"
    }
],
[
    {
        "callId": "1",
        "deadline": null
    },
    {
        "callId": "1",
        "deadline": null
    }
]
]

1 Ответ

0 голосов
/ 02 апреля 2020

Сначала отсортируйте массив по датам, а затем используйте встроенный JavaScript Array Reduce метод

let collection = [
        {
            callId: "1",
            deadline: null
        },
        {
            callId: "1",
            deadline: null
        },
        {
            callId: "3",
            deadline: "2020-04-02T13:37:00.000Z"
        },
        {
            callId: "3",
            deadline: "2020-04-06T08:33:00.000Z"
        },
        {
            callId: "2",
            deadline: null
        },
        {
            callId: "2",
            deadline: "2020-04-06T08:33:00.000Z"
        },
    ]

 // Sort based on date (Null values will be placed at the last)
 collection = collection.sort((a,b) => {
   if (a.deadline === null) {
     return 1;
   }
   else if (b.deadline === null) {
     return -1;
   } else {
     return new Date(a.deadline) - new Date(b.deadline)
   }
})
    
 // convert the array to object using reduce method
 const grouped = collection.reduce((a,c) => ({
   ...a,
   // Check if the key already exist,
   // if yes, append the item to the array
   // or create a new array 
   [c.callId]: a[c.callId] ? [...a[c.callId], c] : [c] 
  }), {})
 
 console.log(grouped)

Упорядочение ключей объектов в JavaScript

Свойства объекта в JavaScript не имеют порядка . Может показаться, что в некоторых браузерах порядок есть, но спецификация ECMAScript определяет порядок перечисления свойств объекта как определяемый реализацией c, поэтому не следует полагать, что поведение одного браузера будет таким же, как и у другого.

Если порядок важен для вас, используйте массивы.

...