JavaScript: Organize an array of objects into separate sections based on a specific field

Presented below is a set of data:

const dataSet = [
  {
    id: '1',
    name: 'River',
    address: 'Terminal A',
    type: 'OTHER',
    code: null,
    targetArrivalStep: 30,
    disabled: true,
  },
  {
    id: '2',
    name: 'Afer',
    address: 'Afer train station',
    type: 'TRAIN_STATION',
    code: 'MTS',
    targetArrivalStep: 0,
    disabled: false,
  },
  {
    id: '3',
    name: 'Fidel',
    address: 'HHH',
    type: 'OTHER',
    code: '',
    targetArrivalStep: 0,
    disabled: false,
  },
  {
    id: '5',
    name: 'Train station',
    address: 'Patrick str.',
    type: 'TRAIN_STATION',
    code: null,
    targetArrivalStep: 0,
    disabled: false,
  },
  {
    id: '7',
    name: 'qqq',
    address: 'qqq',
    type: 'BUS_STATION',
    code: null,
    targetArrivalStep: 60,
    disabled: false,
  },
];

The objective is to categorize this data by the type.

Here is the expected result:

const results = [
  {
    type: 'OTHER',
    data: [
      {
        id: '1',
        name: 'River',
        address: 'Terminal A',
        type: 'OTHER',
        code: null,
        targetArrivalStep: 30,
        disabled: true,
      },
      {
        id: '3',
        name: 'Fidel',
        address: 'HHH',
        type: 'OTHER',
        code: '',
        targetArrivalStep: 0,
        disabled: false,
      },
    ],
  },
  {
    type: 'TRAIN_STATION',
    data: [
      {
        id: '2',
        name: 'Afer',
        address: 'Afer train station',
        type: 'TRAIN_STATION',
        code: 'MTS',
        targetArrivalStep: 0,
        disabled: false,
      },
      {
        id: '5',
        name: 'Train station',
        address: 'Patrick str.',
        type: 'TRAIN_STATION',
        code: null,
        targetArrivalStep: 0,
        disabled: false,
      },
    ],
  },
  {
    type: 'BUS_STATION',
    data: [
      {
        id: '7',
        name: 'qqq',
        address: 'qqq',
        type: 'BUS_STATION',
        code: null,
        targetArrivalStep: 60,
        disabled: false,
      },
    ],
  },
];

My current approach involves using the reduce method, but I am looking for a solution that does not involve mutating reduce arguments. Is there an alternate method to achieve this?

Answer №1

According to the comments, it is acceptable to modify the accumulator since it is newly created for each function call and only changes internally, without any external interruptions. This means that from an external perspective, your solution functions as a pure function without any side effects.

However, for demonstration purposes, you could rework your solution in a declarative manner using some advanced destructuring techniques:

const result = data.reduce((c, item) => ({...c, [item.type]:[...c[item.type] ?? [], item]}), {});

Explanation:

const result = data.reduce(
  (c, item) => ({              // Create a new object
    ...c,                      // Copy previous object properties
    [item.type]: [             // Replace current type group
      ...(c[item.type] ?? []), // Copy existing items of that group (or an empty array)
      item                     // Add the current item
    ] }),
  {}
);

It seems evident, however, that your original solution is more readable and therefore superior.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Sorting objects in an array according to their prices: A guide

Suppose we have the following data structure: var lowestPricesCars = { HondaC: { owner: "", price: 45156 }, FordNew: { owner: "", price:4100 }, HondaOld: { owner: "", price: 45745 }, FordOld: { owner: "", ...

What is the process for transforming a String into an HTML element within a Next JS Application?

I stored the product description as HTML elements in a Database, but when I try to render this data into a div, it displays as a String. I am looking to showcase all the data as HTML elements in my Next JS application. I attempted using JSON.parse, but unf ...

The information displayed in my Google snippet does not match the content of the intended URL

It may seem a bit confusing, so to clarify, here is an example: When you click the +1 button on this page, the snippet will display the text and URL from that specific page. However, in my case, the snippet displays text from the homepage URL instea ...

The submitHandler() function in the jQuery validate method is experiencing delays when executing and processing the form submission

Currently, I am using the jQuery validate method to validate my form. I have implemented some code in the submitHandler() method, but it seems to be taking longer than expected to execute. Can anyone provide me with a solution to resolve this issue? $(&ap ...

Identify the Presence of Hover Functionality

For a while now, the trend has been leaning towards feature detection. I am interested in determining whether a visitor's browser supports the :hover pseudo class. With many mobile devices not supporting hovering, I want to adjust my event listeners a ...

What methods does MaterialUI utilize to achieve this?

Have you checked out the autocomplete feature in their component? You can find it here: https://mui.com/material-ui/react-autocomplete/ I noticed that after clicking on a suggestion in the dropdown, the input box retains its focus. How do they achieve thi ...

Adding flair to a fresh element and then removing it upon its inception

I'm working with a JavaScript code that creates a new element when a button is clicked. I have a question about it. Here's the JavaScript code snippet: var comment = document.querySelector("#AddComment"); var req = new XMLHttpRequest(); if(comm ...

Determining the best use-case for a React framework like Next or Gatsby versus opting for Create React App

As I delve into the world of React and JavaScript, I find myself in the fast-paced prototyping stage. I can't help but ponder at what point developers choose to utilize frameworks like Next.js or Gatsby.js over the usual Create React App. I'm pa ...

Retrieve JSON object by matching another JSON property

I am working with an array of id's and their respective contents in a JSON response. My goal is to retrieve the content based on the received id. For instance, if the ID is 1 (returned from the JSON), I aim to access the JSON data using "data.id" (wh ...

What could be the reason for my inability to retrieve req.user.username with passport.js?

I recently started using passport.js for authentication and I'm encountering an issue. When I log in via Google, the only information available to me through req.user is the user id. I have provided my passport setup code, along with the routes, hopin ...

Tips for obtaining latency measurements from the DailyMotion player during a live video stream

Is there a way to determine the latency of DailyMotion live video for synchronization with events, such as displaying speaker names alongside the video? I have been utilizing the DailyMotion player API in JavaScript but haven't found any information r ...

Creating a List with Sublists that are displayed when hovering over the parent List is a key element of effective design

Hovering over 'View Rows' should open up both New Records and Old Records <div> <li>Add Rows</li> <li>DeleteRows</li> <li>View Rows <ul> <li>View New Records</li ...

Persuading on the Server-Side

After reading through the Google-Caja wiki, I became intrigued by its capabilities. From what I understand, with Caja we can send a snippet of HTML (such as a ) to Google-Caja's server (cajoling service) for processing. The HTML is cajoled and the Jav ...

"Learn how to seamlessly submit a form without reloading the page and send data back to the same page using Node and Express

I've already reviewed a few questions on this platform. They all focus on submitting post requests, but I believe the process should be similar for get requests as well. Therefore, I made modifications to my code to accommodate get requests. However, ...

Output Scalable Vector Graphics (SVG) content on a webpage

I need to include an SVG element in my Angular 2+ code. My goal is to provide users with the option to print the SVG element as it appears on the screen. <div class="floor-plan" id="printSectionId2" (drop)="onDrop($event)" (dragover)="onDragOver ...

What is the best way to extract the last JSON object from a JSONArray based on a specified value

I am currently working with a JSONArray that looks like the following: [ { "id": 1, "firstName": "abc", "isActive": true }, { "id": 2, "firstName": "cde", "isActive": false }, { " ...

Save the JWT token securely within a closure

Someone mentioned that the recommended way to store JWT tokens is as follows: access_token in the application memory (like closures) refresh_token in cookie entries (HttpOnly) Currently, my access_token is stored in localStorage and used for checking aut ...

The concept of recursively exporting modules in Node.js modules

Looking for a way to recursively export all .hbs files in a NodeJS 14+ project main JS. I attempted the following: module.exports = () => ({ partial : __dirname + "/../partial/**.hbs", helper : __dirname + "/../helper/*.js" } ...

Retrieve geographical coordinates from image metadata using JavaScript

Seeking help with extracting the GPS Exif tag from images using NodeJS. The data is currently structured as follows: { "gps": { "GPSTimeStamp": [2147483647, 76, 41], "GPSLongitude": [76, 41, 56.622], "GPSLatitude": [30, 43, 8 ...

Converting a unix timestamp to a Date in TypeScript - a comprehensive guide

To retrieve the unix timestamp of a Date in plain JavaScript and TypeScript, we can use this code snippet: let currentDate = new Date(); const unixTime = currentDate.valueOf(); Converting the unix timestamp back to a Date object in JavaScript is straight ...