Conditionally manipulate elements' properties in array

Viewed 49

I'm new to javascript and trying to learn some basic with toy examples.

Say I have an array containing data on six people.

const myArray = [
    {"id": 1, "value": 75, "friends": 3},
    {"id": 2, "value": 40, "friends": 4},
    {"id": 3, "value": 60, "friends": 5},
    {"id": 4, "value": 62, "friends": 6},
    {"id": 5, "value": 55, "friends": 1},
    {"id": 6, "value": 33, "friends": 2}
];

The array lists each person's id, value, and who they're friends with. E.g., Person 1 is friends with person 3, and person 3 is friends with person 5, and so on.

Now I want to manipulate who is friends with who based on each person's value. This is the logic I'd like to implement (probably in a for loop):

IF person's value is the lowest or the second lowest value in the array, THEN add the id of the person with the highest value in the array to their friends.

So my desired output in this case is:

const myArray = [
    {"id": 1, "value": 75, "friends": 3},
    {"id": 2, "value": 40, "friends": [4, 1]},
    {"id": 3, "value": 60, "friends": 5},
    {"id": 4, "value": 62, "friends": 6},
    {"id": 5, "value": 55, "friends": 1},
    {"id": 6, "value": 33, "friends": [2, 1]}
];

How can I do this?


I've done a very basic manipulation of the array below, where I take away the friend of the person with the highest value in the array. But I've gotten confused as I've moved onto this more complicated task.

const myArray = [
    {"id": 1, "value": 75, "friends": 3},
    {"id": 2, "value": 40, "friends": 4},
    {"id": 3, "value": 60, "friends": 5},
    {"id": 4, "value": 62, "friends": 6},
    {"id": 5, "value": 55, "friends": 1},
    {"id": 6, "value": 33, "friends": 2}
];

// Finds max and min values in array
var highest = Number.NEGATIVE_INFINITY;
var tmp;
for (var i=myArray.length-1; i>=0; i--) {
    tmp = myArray[i].value;
    if (tmp > highest) highest = tmp;
};

for(i = 0; i < myArray.length; i++){
    // If person has the highest value in the array
      if(myArray[i].value == highest){
        // Then take away their friend
        myArray[i].friends = NaN
      } else {
        myArray[i].friends = myArray[i].friends
      }
  };

  console.log(myArray);

2 Answers

You may pass your source array once to figure out the highest, the lowest and the second lowest values (along with corresponding id's), then modify your source array accordingly when you reach the end:

const src = [
    {"id": 1, "value": 75, "friends": 3},
    {"id": 2, "value": 40, "friends": 4},
    {"id": 3, "value": 60, "friends": 5},
    {"id": 4, "value": 62, "friends": 6},
    {"id": 5, "value": 55, "friends": 1},
    {"id": 6, "value": 33, "friends": 2}
],
    
    populateFriends = input => {
      let highest = {value: -Infinity},
          lowest = {value: Infinity},
          secondLowest = {}
      for({id, value} of input){
          if(value > highest.value){
            highest = {id, value}
          } else if(value < lowest.value){
            secondLowest = {...lowest}
            lowest = {id, value}
          }
      }
      return input.map(o => 
        (o.id == lowest.id || o.id == secondLowest.id) && 
        o.friends != highest.id ? 
        {...o, friends: [o.friends, highest.id]} :
        o)
    }
    
console.log(populateFriends(src))
.as-console-wrapper{min-height:100%;}

You can do it so

const myArray = [
    {"id": 1, "value": 75, "friends": 3},
    {"id": 2, "value": 40, "friends": 4},
    {"id": 3, "value": 60, "friends": 5},
    {"id": 4, "value": 62, "friends": 6},
    {"id": 5, "value": 55, "friends": 1},
    {"id": 6, "value": 33, "friends": 2}
];

const highestValue = myArray.reduce((acc, rec) => {
  return (acc.value < rec.value) ? acc = rec : acc
}, myArray[0])

const twoLowestPersons = myArray.sort((a, b) => a.value - b.value).slice(0, 2)

const result = myArray.map(rec => {
  const object = twoLowestPersons.find(el => el.id === rec.id)
  if (typeof object !== 'undefined') {
    rec.friends = [rec.friends, highestValue.id]
    return rec
  } else {
    return rec
  }
}).sort((a, b) => a.id - b.id)

console.log(JSON.stringify(result))

Related