0

i have a Question. I was thinking long Time about it, but poorly i don´t find a answer. I know the every method.

My Question is about this code section:

var tr = order.every((i) => stock[i[0]] >= i[1]);

My Questions are:

  1. stock is an Object. Why i must write as an array?

  2. Why it is i[0] in stock and then i[1] ?

  3. Why this code checks the nested Arrays in const order ?

const order = [
  ["shirt", 5],
  ["shoes", 2]
];

const stock = {
  shirt: 50,
  height: 172,
  mass: 120,
  shoes: 6
};

var tr = order.every((i) => stock[i[0]] >= i[1]); /// return true
console.log(`tr:`,tr)
phuzi
  • 12,078
  • 3
  • 26
  • 50
  • 1
    You're not treating `stock` as an array, you're using _bracket notation_. See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Property_Accessors . See also https://stackoverflow.com/questions/4244896/dynamically-access-object-property-using-variable – Teemu May 27 '22 at 07:45
  • @Teemu Thank you very much. And why it must be greater or equal to i[1] ? – DevMakesSmarter May 27 '22 at 07:47
  • 1
    That's a condition for an acceptable order, most likely it prevents you to buy more products than there are in the storage. – Teemu May 27 '22 at 07:49

5 Answers5

2

So, the square brackets can be used to access element inside the array by passing it's index e.g:

const arr = ["first", "second"];
const secondElement = arr[1] // index 1 means seconds element

and also square brackets can be used to access element inside the object by passing it's key e.g:

const obj = { first: 1, second: 2 };
const secondElement = object.second // Normal way to access value in object
const secondElementWithAnotherSyntax = object['second'] // another syntax, same thing

the cool thing about the other syntax shown is that you can pass variable to it, e.g :

const objKey = 'second'
const secondElement = obj[objKey]

Now let's look at your example, i is one element of the array order, which carries arrays itself, so i is also one of the two small arrays, i[0] is the string word in the beginning of the small arrays, so:

i[0] // is either 'shirt' or 'shoes' and since stocks is an object that has those keys, you can access for example the value 50 by saying stocks['shirt'] or as in your case, stock[i[0]] ;)

now your second question: why should it be >= i[1] ? because the order second item , aka i[1] is the number of items required/ordered, so this should always be less that your stock, you can't by 5 shirts from a place that has only 3 in the stock :)

Yasser hennawi
  • 735
  • 4
  • 10
2

May I suggest to try to use more expressive naming of the variables ?

An object property can be accessed through bracket notation, as in stock[orderedProductName] when using a variable - Property accessors

A concise but imho more readable version can be written using destructuring assignment

const order = [
  ["shirt", 5],
  ["shoes", 2]
];

const stock = {
 shirt: 50,
 height: 172,
 mass: 120,
 shoes: 6,
};

// original version

let inStock = order.every((i) => stock[i[0]] >= i[1]); /// return true


// more verbose version
// check if every item in array order satisfies the condition
// let's cycle over the array calling the element we're working on
// orderItem

inStock = order.every( orderItem => {
  const orderedProductName = orderItem[0];
  const orderedProductQuantity = orderItem[1];
  // to access an object property we can use bracket notation
  const stockProductQuantity = stock[orderedProductName];
  
  // the condition to check: do we have enough products in stock ?
  return stockProductQuantity >= orderedProductQuantity;
});


// a concise variation could make use of destructuring assignment.
// Here, when we take the order item array, we immediately assign
// each of its elements to the appropriate variable
//
// orderItem[0] or first array element -> productName
// orderItem[1] or second array element -> orderedQuantity

inStock = order.every(([productName, orderedQuantity]) => 
  stock[productName] >= orderedQuantity
);

if(inStock) {
  console.log('pack and ship');
}
else {
  console.log('need to restock'); 
}
giulp
  • 2,200
  • 20
  • 26
2

1. stock is an Object. Why i must write as an array?

You can access properties of objects using brackets [].

Why do we need this?

  1. To be able to access properties of objects dynamically, e.g. when you are looping though keys and want to get the values
Object.keys(data).forEach(function(key) {
  console.log('Key : ' + key + ', Value : ' + data[key])
})
  1. Sometimes there is no other way to access the value:
const json = {
  "id":"1",
  "some key with spaces": "48593"
};

console.log(json.some key with spaces); // obviously throws error
console.log(json['some key with spaces']); // prints "48593"

2. Why it is i[0] in stock and then i[1] ?

3. Why this code checks the nested Arrays in const order ?

The code goes through the orders, each order is an array so i[0] is the type of the order and i[1] is the quantity. the code checks if there are enough items in stock. To check if there are enough shirts you would do:

console.log(stock["shirts"] >= 5)

Thats what the code in your example does, it just passes the key ("shirts") and quantity (5) dynamically.

Haris Bouchlis
  • 2,366
  • 1
  • 20
  • 35
0

The every() method tests whether all elements in the array pass the test implemented by the provided function. It returns a Boolean value. If you want to read more Array.prototype.every()

In your code snippet you are checking that every item in order array has quantity less than the quantity available in stock.

To access the properties of a object you can use square notation also like arrays. To read more Bracket Notation

Shikhar Awasthi
  • 1,172
  • 1
  • 3
  • 13
0

If you assigned more meaningful variables to the code you'd probably understand how this works better.

In one order (an array) we have two nested arrays. The first describes shirt/value, the other shoes/value. every is going to see if there is enough stock for both shirt and shoes by checking that the stockValue >= the items in the order.

When you every over the order array the callback for each iteration is one orderItem (['shirt', 5] first, then ['shoes', 2] for the second). We can assign the first element of each array to a variable called itemType, and the second to a variable called itemQty.

So when you see stock[i][0] we can translate that in the new code as stock[orderType] which is using bracket notation to locate the property value associated by that key in the stock object. We then check to see if that value >= than the itemQty.

const order=[["shirt",5],["shoes",2]],stock={shirt:50,height:172,mass:120,shoes:6};

const result = order.every(orderItem => {
  const itemType = orderItem[0];
  const itemQty = orderItem[1];
  return stock[itemType] >= itemQty;
});

console.log(result);
Andy
  • 61,948
  • 13
  • 68
  • 95