Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Sort array on two different values and keep flat array structure

I have this array

const rows = [
    {data: [{text: "A",value: 100}, {text: "B",value: 74}], group: "Elephant"},
    {data: [{text: "C",value: 63}, {text: "D",value: 1}], group: "Elephant"},
    {data: [{text: "E",value: 37}, {text: "F",value: 54}], group: "Penguin"},
    {data: [{text: "G", value: 72}, {text: "H", value: 74}], group: "Lion"},
    {data: [{text: "K", value: 76}, {text: "L", value: 38}], group: "Zebra"},
    {data: [{text: "M", value: 68}, {text: "N", value: 21}], group: "Lion"},
];

And these sort functions

const _sortFunction = (
    a,
    b,
    columnIndex,
    sortOrder
) => {
    if (a && a.data && b && b.data) {
        if (a.data[columnIndex].value === b.data[columnIndex].value) {
            return 0;
        } else {
            if (sortOrder === "ASC") return a.data[columnIndex].value > b.data[columnIndex].value ? -1 : 1;
            if (sortOrder === "DESC") return a.data[columnIndex].value < b.data[columnIndex].value ? -1 : 1;
            return 0;
        }
    } else {
        return 0;
    }
};

const sortRowsByColumn = (rows, sortProps) => {
    if (sortProps && rows) {
        const {indexOfColumnToSort, sortOrder} = sortProps;
        const rowsCopy = JSON.parse(JSON.stringify(rows))
        return rowsCopy.sort((a, b) => _sortFunction(a, b, indexOfColumnToSort, sortOrder));
    }
    return rows;
};

Which gives me console.log(sortRowsByColumn(rows, {indexOfColumnToSort: 1, sortOrder: "ASC"}))

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

[
{data: [{text: "A", value: 100}, {text: "B", value: 74}], group: "Elephant"}, 
{data: [{text: "G", value: 72}, {text: "H", value: 74}], group: "Lion"}, 
{data: [{text: "E", value: 37}, {text: "F", value: 54}], group: "Penguin"}, 
{data: [{ text: "K", value: 76}, {text: "L", value: 38}], group: "Zebra"}, 
{data: [{text: "M", value: 68}, {text: "N", value: 21}], group: "Lion"}, 
{data: [{text: "C", value: 63}, {text: "D", value: 1}],group: "Elephant"}
]

However, what I cannot get my head around is the following:
The updated sortRowsByColumn() function should

  1. sort the rows array based on the group key (alphabetically)
  2. then sort based on the column index for each group

all of this without loosing the original array structure. Basically like a grouping and sorting for each group, without modifiying the array structure or the original array.
The result should look like this

[
{data: [{text: "A",value: 100}, {text: "B", value: 74}], group: "Elephant"}, 
{data: [{text: "C", value: 63}, {text: "D", value: 1}], group: "Elephant"}, 
{data: [{text: "G", value: 72}, {text: "H", value: 74}], group: "Lion"}, 
{data: [{text: "M", value: 68}, {text: "N", value: 21}], group: "Lion"},
{data: [{text: "E",value: 37}, {text: "F", value: 54}], group: "Penguin"}, 
{data: [{text: "K", value: 76}, {text: "L", value: 38}], group: "Zebra"}, 
]

>Solution :

I add sample code below.

const _sortFunction = (
  a,
  b,
  columnIndex,
  sortOrder
) => {
  if (a && a.data && b && b.data) {
    if (a.data[columnIndex].value === b.data[columnIndex].value) {
      return 0;
    } else {
      if (sortOrder === "ASC") return a.data[columnIndex].value > b.data[columnIndex].value ? -1 : 1;
      if (sortOrder === "DESC") return a.data[columnIndex].value < b.data[columnIndex].value ? -1 : 1;
      return 0;
    }
  } else {
    return 0;
  }
};


const sortRowsByColumn = (rows, sortProps) => {
  if (!sortProps || !rows) {
    return rows;
  }

  const {
    indexOfColumnToSort,
    sortOrder
  } = sortProps;

  const groupedAndSortedRows = [...rows].sort((a, b) =>
    a.group.localeCompare(b.group) || _sortFunction(a, b, indexOfColumnToSort, sortOrder)
  );

  groupedAndSortedRows.forEach(row =>
    row.data.sort((a, b) => _sortFunction(a, b, indexOfColumnToSort, sortOrder))
  );

  return groupedAndSortedRows;
};




// Example usage
const rows = [
    {data: [{text: "A",value: 100}, {text: "B",value: 74}], group: "Elephant"},
    {data: [{text: "C",value: 63}, {text: "D",value: 1}], group: "Elephant"},
    {data: [{text: "E",value: 37}, {text: "F",value: 54}], group: "Penguin"},
    {data: [{text: "G", value: 72}, {text: "H", value: 74}], group: "Lion"},
    {data: [{text: "K", value: 76}, {text: "L", value: 38}], group: "Zebra"},
    {data: [{text: "M", value: 68}, {text: "N", value: 21}], group: "Lion"},
];
console.log(sortRowsByColumn(rows, {
  indexOfColumnToSort: 1,
  sortOrder: "ASC"
}));
  • I first sort the rows array based on the "group" key using localeCompare for alphabetical sorting.

  • Then, I map over the sorted rows and sort the data array within each group based on the specified column index using the existing _sortFunction.

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading