3

I have this Object:

{
  "data": {
    "success": true,
    "historical": true,
    "date": "2022-01-01",
    "base": "MXN",
    "rates": {
      "COFFEE": 0.02158734144632395,
      "CORN": 0.008232645172711363,
      "COTTON": 0.04320921676820366,
      "SOYBEAN": 0.0036714622235960175,
      "SUGAR": 0.25680398615582695,
      "WHEAT": 0.00017592643558262669
    },
    "unit": "per bushel"
  }
}  

And I want to iterate over "rates" to replace the values of each key with 1 / value
I tried with: (prueba is the Object name)

Object.values(this.prueba.data.rates).forEach((val) => {
      console.log(val)
      val = 1 / val;
      console.log(val)
    })

But how to replace those values or how can I saved them in another array or Object

Chris
  • 322
  • 6
  • 19

4 Answers4

3

Your code doesn't work because the change you made to val is only reflected within the scope of the callback.

You should instead loop through each property and set its value.

const obj={data:{success:!0,historical:!0,date:"2022-01-01",base:"MXN",rates:{COFFEE:.02158734144632395,CORN:.008232645172711363,COTTON:.04320921676820366,SOYBEAN:.0036714622235960175,SUGAR:.25680398615582695,WHEAT:.00017592643558262669},unit:"per bushel"}};

let r = obj.data.rates;
Object.keys(r).forEach(e => r[e] = 1 / r[e])
console.log(obj)

If you're using Typescript it's necessary to declare the object like so:

const obj: {[key: string]: any} = ...
Spectric
  • 30,714
  • 6
  • 20
  • 43
  • 1
    Thank you, but I have an error Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{ COFFEE: number; CORN: number; COTTON: number; SOYBEAN: number; SUGAR: number; WHEAT: number; }'. No index signature with a parameter of type 'string' was found on type '{ COFFEE: number; CORN: number; COTTON: number; SOYBEAN: number; SUGAR: number; WHEAT: number; }'.ts(7053) I'm using typescript, so its setting e to a string type – Chris May 15 '22 at 02:00
  • 2
    Just solve it with the answer on this question https://stackoverflow.com/questions/57438198/typescript-element-implicitly-has-an-any-type-because-expression-of-type-st Thank you, could you just edit your answer with const obj: {[key: string]: any} ={} so if anyone with the problem can solve it, once again than you so much – Chris May 15 '22 at 02:19
2

You can iterate over Object.entries (or Object.keys) and replace the value for each key.

let obj={data:{success:!0,historical:!0,date:"2022-01-01",base:"MXN",rates:{COFFEE:.02158734144632395,CORN:.008232645172711363,COTTON:.04320921676820366,SOYBEAN:.0036714622235960175,SUGAR:.25680398615582695,WHEAT:.00017592643558262669},unit:"per bushel"}};
Object.entries(obj.data.rates).forEach(([k, v]) => obj.data.rates[k] = 1 / v);
console.log(obj);
Unmitigated
  • 76,500
  • 11
  • 62
  • 80
  • Thank you but I have the same error as using @Spectric answer: Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{ COFFEE: number; CORN: number; COTTON: number; SOYBEAN: number; SUGAR: number; WHEAT: number; }'. No index signature with a parameter of type 'string' was found on type '{ COFFEE: number; CORN: number; COTTON: number; SOYBEAN: number; SUGAR: number; WHEAT: number; }'.ts(7053) – Chris May 15 '22 at 02:01
1

I think it will be cleaner to write it explicitly using for loops:

let obj = {} //original object stated in question
let obj2 = Object.create(null);//DON'T just use {}, see below
for(let productName in obj.data.rates){
   let inverse = 1/obj.data.rates[productName];
   //to edit the object directly
   obj.data.rates[productName] = inverse;
   //to add to another object
   obj2[productName] = inverse;
}

The difference between {} and Object.create(null) can be found here

wyvern
  • 116
  • 1
  • 7
1

You can combine Object.entries(), Array#forEach() and Destructuring assignment

Code:

const obj = {data:{success:0,historical:0,date:"2022-01-01",base:"MXN",rates:{COFFEE:.02158734144632395,CORN:.008232645172711363,COTTON:.04320921676820366,SOYBEAN:.0036714622235960175,SUGAR:.25680398615582695,WHEAT:.00017592643558262669},unit:"per bushel"}}

const replaceValue = ({ data: { rates: r }}) => 
  Object
    .entries(r)
    .forEach(([k, v]) => r[k] = 1 / v)

replaceValue(obj)

console.log(obj)
Yosvel Quintero
  • 18,669
  • 5
  • 37
  • 46