0

I am attempting to merge a "fresh shipment" array with a current inventory array by first creating object to make the data more manageable. So, any same-items are added to any existing ones in inventory.

.sort runs but flat doesn't seem to do anything. I suspect there is some kind of issues related to how I made the array and messing up the indices?

function updateInventory(arr1, arr2) {
    let invObj = {}
    let updateObj = {}
    let result = []

    arr1.forEach( x => invObj[x[1]] = x[0])
    arr2.forEach( x => updateObj[x[1]] = x[0])

    for(let key in updateObj) {
        if (invObj[key]) {
            invObj[key] += updateObj[key]
        } else {
            invObj[key] = updateObj[key]
        }
    }

    result =  Object.keys(invObj).map(key=>[invObj[key],key])
    .sort((a,b)=>{
    // attempting to sort inventory alphabetically here as required by my course's test
        return a[1] - b[1]
    })

    return result
}
var curInv = [
    [21, "Bowling Ball"],
    [2, "Dirty Sock"],
    [1, "Hair Pin"],
    [5, "Microphone"]
];

var newInv = [
    [2, "Hair Pin"],
    [3, "Half-Eaten Apple"],
    [67, "Bowling Ball"],
    [7, "Toothpaste"]
];

console.log(updateInventory(curInv, newInv));

3
  • 2
    If you are trying to sort strings, using subtraction is inappropriate. You should use the localeCompare method off of the strings. Commented May 14, 2020 at 21:37
  • Also, might I suggest sorting the keys before you build out the final result. Could make your code a little cleaner Commented May 14, 2020 at 21:38
  • As others have written, use localCompare to compare strings. Your sort test should read return a[1].localeCompare(b[1]); Commented May 14, 2020 at 21:48

4 Answers 4

3

You should use the localeCompare method when sorting string values.

function updateInventory (arr1, arr2) {
  let invObj = {};
  let updateObj = {};
  let result = [];

  arr1.forEach(x => invObj[x[1]] = x[0]);
  arr2.forEach(x => updateObj[x[1]] = x[0]);

  for (let key in updateObj) {
    if (invObj[key]) {
      invObj[key] += updateObj[key];
    } else {
      invObj[key] = updateObj[key];
    }
  }

  result = Object.keys(invObj)
    .sort((a, b) => a.localeCompare(b))
    .map(key => [invObj[key], key]);

  return result;
}

var curInv = [
  [21, 'Bowling Ball'],
  [2, 'Dirty Sock'],
  [1, 'Hair Pin'],
  [5, 'Microphone']
];

var newInv = [
  [2, 'Hair Pin'],
  [3, 'Half-Eaten Apple'],
  [67, 'Bowling Ball'],
  [7, 'Toothpaste']
];

console.log(
  updateInventory(curInv, newInv)
);

Sign up to request clarification or add additional context in comments.

Comments

0

Are you looking for the array to be in the same format as your data in the first instance?

function updateInventory(arr1, arr2) {
    let invObj = {}
    let updateObj = {}
    let result = []

    arr1.forEach( x => invObj[x[1]] = x[0])
    arr2.forEach( x => updateObj[x[1]] = x[0])

    for(let key in updateObj) {
        if (invObj[key]) {
            invObj[key] += updateObj[key]
        } else {
            invObj[key] = updateObj[key]
        }
    }
    
    return invObj;
}
var curInv = [
    [21, "Bowling Ball"],
    [2, "Dirty Sock"],
    [1, "Hair Pin"],
    [5, "Microphone"]
];

var newInv = [
    [2, "Hair Pin"],
    [3, "Half-Eaten Apple"],
    [67, "Bowling Ball"],
    [7, "Toothpaste"]
];

console.log(updateInventory(curInv, newInv));

Comments

0

When sorting strings it's a little more complicated because you have to take into account capitalization as well. This is a snippet from a table I made in js, hopefully it helps. You can use localecompare as well like taplar said.

            .sort(
                function(a,b) {
                    a = a[1];
                    b = b[1];
                    if (a < b) {
                        return -1; 
                    } else if (a > b) {
                        return 1;
                    } else {
                        return 0; // Equal
                    }
                });

Comments

0

I would make a lookup object and keep references to the array items. After I loop over the current items, I would loop over the new items. Check to see if it exists and update the count. If it does not exist add the item to the inventory.

var curInv = [
    [21, "Bowling Ball"],
    [2, "Dirty Sock"],
    [1, "Hair Pin"],
    [5, "Microphone"]
];

var newInv = [
    [2, "Hair Pin"],
    [3, "Half-Eaten Apple"],
    [67, "Bowling Ball"],
    [7, "Toothpaste"]
];

// make a look up object to reference by the key
var lookup = curInv.reduce( (obj, item) => ({ ...obj, [item[1]]: item }), {})

// loop over the new inventory and add it on
newInv.forEach((item) => {
  // check to see if we have the item
  var key = item[1]
  var exisiting = lookup[key]
  // if exists add it
  if (exisiting) {
    exisiting[0] += item[0]
  } else {
    // new item
    // add to our look up table in case it repeats
    lookup[key] = item
    // add it to the inventory list
    curInv.push(item)
  }
})

console.log(curInv)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.