Modifying object parameters in an array based on their similarity: A guide

I've encountered an array of objects like this:

const data = [
  { position: 1, name: "a", score: 9000 },
  { position: 2, name: "b", score: 8000 },
  { position: 3, name: "c", score: 6000 },
  { position: 3, name: "c", score: 6000 },
  { position: 4, name: "d", score: 6000 },
  { position: 5, name: "e", score: 6000 },
  { position: 6, name: "f", score: 6000 },
  { position: 7, name: "g", score: 4000 },
  { position: 8, name: "h", score: 3000 },
  { position: 9, name: "i", score: 2500 },
  { position: 10, name: "j", score: 2500 },
  { position: 11, name: "k", score: 1000 },
  { position: 12, name: "l", score: 1000 },
];

My goal is to loop through it using basic JavaScript to achieve this desired outcome:

const data = [
  { position: "1", name: "a", score: 9000 },
  { position: "2", name: "b", score: 8000 },
  { position: "3-6", name: "c", score: 6000 },
  { position: "3-6", name: "c", score: 6000 },
  { position: "3-6", name: "d", score: 6000 },
  { position: "3-6", name: "e", score: 6000 },
  { position: "3-6", name: "f", score: 6000 },
  { position: "7", name: "g", score: 4000 },
  { position: "8", name: "h", score: 3000 },
  { position: "9-10", name: "i", score: 2500 },
  { position: "9-10", name: "j", score: 2500 },
  { position: "11-12", name: "k", score: 1000 },
  { position: "11-12", name: "l", score: 1000 },
];

I've experimented with several methods, but none have yielded the desired result. Any suggestions on how to accomplish this? Thank you in advance.

This function is the closest I've come so far:

function placement() {
  let repeat=0;
  for (let i = 0; i < data.length; i++) {
    let counter = 0;
    for (let j = 0; j < data.length; j++) {
      if (data[i].score == data[j].score) {
        if(data[i].position==data[j].position){
          repeat++;
        }
        counter++;
      }
    }
    if (counter > 1) {
      let k;
      let start=data[i].position;
      for (k = i; k < i + counter-1; k++) {
        data[k].position =
          start + "-" + data[i + counter-1].position;
      }
      i=k;
    }
  }
}

Answer №1

To begin, you can group by the score first and then assign a position to each group accordingly.

const
    data = [{ position: 1, name: "a", score: 9000 }, { position: 2, name: "b", score: 8000 }, { position: 3, name: "c", score: 6000 }, { position: 3, name: "c", score: 6000 }, { position: 4, name: "d", score: 6000 }, { position: 5, name: "e", score: 6000 }, { position: 6, name: "f", score: 6000 }, { position: 7, name: "g", score: 4000 }, { position: 8, name: "h", score: 3000 }, { position: 9, name: "i", score: 2500 }, { position: 10, name: "j", score: 2500 }, { position: 11, name: "k", score: 1000 }, { position: 12, name: "l", score: 1000 }],
    result = data
        .reduce((r, o, i, a) => {
            if (!i || a[i - 1].score !== o.score) r.push([]);
            r[r.length - 1].push(o);
            return r;
        }, [])
        .flatMap(a => a.map((o, i, b) => b.length === 1
            ? o
            : { ...o, position: `${b[0].position}-${b[b.length - 1].position}` }
        ));

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

Answer №2

Given that the elements in the data array are arranged in ascending order based on the score, meaning each unique score is represented once, you can achieve the following:

  1. Traversal of the array can be done using Array#reduce method while updating a Map where the score serves as the key, and its starting and ending positions are stored as the value.
  2. Subsequently, by using Array#map, loop through the array again, and for each element, assign the position based on the values retrieved from the Map:

const data = [
  { position: 1, name: "a", score: 9000 },
  { position: 2, name: "b", score: 8000 },
  { position: 3, name: "c", score: 6000 },
  { position: 3, name: "c", score: 6000 },
  { position: 4, name: "d", score: 6000 },
  { position: 5, name: "e", score: 6000 },
  { position: 6, name: "f", score: 6000 },
  { position: 7, name: "g", score: 4000 },
  { position: 8, name: "h", score: 3000 },
  { position: 9, name: "i", score: 2500 },
  { position: 10, name: "j", score: 2500 },
  { position: 11, name: "k", score: 1000 },
  { position: 12, name: "l", score: 1000 },
];

const scoreMap = data.reduce((map, { position, score }) => {
  const { start } = map.get(score) || {};
  if(start) (map.get(score)).end = position;
  else map.set(score, { start: position });
  return map;  
}, new Map);

const res = data.map(e => { 
  const { start, end } = scoreMap.get(e.score);
  return { ...e, position: end ? `${start}-${end}` : `${start}` };
});

console.log(res);

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

Implementing a delay between two div elements using jQuery

I have two Divs with the class "sliced", each containing three images with the class "tile". When I animate using jQuery, I am unable to add a delay between the "sliced" classes. However, I have successfully added a delay between the "tile" classes. index ...

Getting the output from AJAX when the onreadystatechange event occurs

Struggling with retrieving a value from a function and storing it in a variable? Getting an "undefined" result due to JavaScript's asynchronous nature? Unsure how to fix this using "callbacks" or "promises"? Check out the code snippet below. The goal ...

What could be the reason for the undefined initial state in my vuex store?

I am facing an issue with vuex-typescript where the initial state is always undefined. However, it works fine when I reset the state and refresh the window. Below is my setup for a simple module: import Vue from "vue"; import Vuex from "vuex"; import { m ...

How to use jquery and ajax to retrieve an array of data and show it on the screen

I am facing an issue with my ajax request. Actually, I am unsure of how to fetch multiple records. I attempted the following: $rqt = "SELECT a,b,c from table"; $res = mysql_query($rqt); while ($data = mysql_fetch_assoc($res)): $objet = $d ...

Which design pattern would be best suited for monitoring the completion of multiple ajax requests?

In my code, I have combined 3 separate ajax calls in one function along with checkAjaxCompletion method to monitor each ajax completion flag. The current approach involves sending multiple independent ajax calls and using an interval method to continuousl ...

Creating a customizable 2D register/ array in Verilog with dynamic size dimensions

I have been working on incorporating a genetic algorithm into an FPGA. My goal is to create the initial population by using a 2D array with user input from switches. However, I have encountered an issue where the signal is not recognized as a constant wh ...

Issue with initializing MdTable in Vue Material when fetching data

After encountering a null error while trying to fetch remote data to initialize the MdTable component, I shared my issue here. The data is retrieved from a MySQL database as part of a Laravel 5.6 API project. Upon thorough investigation, it seems that the ...

Tips for sending context in the success callback function of a jQuery AJAX request

const Box = function(){ this.parameters = {name:"rajakvk", year:2010}; Box.prototype.callJsp = function() { $.ajax({ type: "post", url: "some url", success: this.executeSuccess.bind(this), err ...

How can I prevent Heroku from automatically running the script with 'npm start'?

I am currently in the process of developing a server-based application that utilizes automated scripts, also known as "bots," within a cloud environment. I have set up Heroku Scheduler to execute one of these scripts automatically, as illustrated in Figure ...

The disappearance of the checkbox is not occurring when the text three is moved before the input tag

When I move text three before the input tag, the checkbox does not disappear when clicked for the third time. However, if I keep text three after the input tag, it works fine. Do you have any suggestions on how to fix this issue? I have included my code be ...

After the installation of Windows 10 and the latest version of NodeJS, Gatsby seems to be

The gatsby project I set up following the official website instructions seems to be malfunctioning. NodeJS version: v16.15.0, npm version: 8.8.0, gatsby version: 4.13.0, gatsby CLI version: 4.13.0 C:\Users\Dell\Desktop\New folder&bsol ...

Reading Properties in VueJS with Firebase

<template> <div id="app"> <h1 id="title"gt;{{ quiz.title }}</h1> <div id="ques" v-for="(question, index) in quiz.questions" :key="question.text"> <div v-show="index = ...

Edit data with modal form in Angular-UI

Currently in the process of developing a single page todo application using AngularJs and Angular-Ui. Encountering difficulties when attempting to edit a todo item at this stage. The plan is to utilize a modal window for editing information, successfully ...

Can a for loop iterate through a conditional statement using the length property?

Glad you're here to check this out. See the code below. let questions = []; let Question = function(question, answers, number) { this.question = question; this.answers = answers; this.number = number; } let question1 = new Question(&ap ...

Desiring the ability to retrieve a JSON response from a Laravel controller for use in my javascript code

I am trying to figure out the best way to fetch data from my Laravel controller and show it using JavaScript on a webpage. How should I approach this? Here is the code snippet of my controller and ajax call: var jq = jQuery.noConflict(); var id = jq(" ...

Arrange a jQuery data table by British date format and exclude any empty cells

Is there a way to ensure the empty cell remains at the bottom when sorting dates in the dd/mm/yyyy format? I am encountering issues with this aspect in sorting the age column. Here is the link to my problem: http://jsfiddle.net/dup75/11/ $('#hr_curri ...

Is there a Page Views tracker in sinatra?

Help needed with implementing a page views counter using Sinatra and Ruby. I attempted using the @@ variables, but they keep resetting to zero every time the page is reloaded... Here's an example: Appreciate any advice! ...

Errors occur when using jQuery Autocomplete alongside Angular HTTP

I have implemented an ajax autocomplete feature for my database using the jQuery-Autocomplete plugin. Below is my current code setup: HTML: <input ng-keyup="searchCustomer()" id="customerAutocomplete" type="text"> Angular $scope.searchCustome ...

Is there a way in JavaScript to format an array's output so that numbers are displayed with only two decimal places?

function calculateTipAmount(bill) { var tipPercent; if (bill < 50 ) { tipPercent = .20; } else if (bill >= 50 && bill < 200){ tipPercent = .15; } else { tipPercent = .10; } return tipPercent * bill; } var bills = ...

Creating a unique filter that combines and filters data from two separate API calls for

In my current scenario, I am making two different API calls using Axios in my application. The first call fetches a complete JSON file that populates a table, while the second call retrieves only categories. This setup is due to the complexity of the app, ...