访问对象

时间:2018-11-21 05:10:06

标签: javascript arrays javascript-objects for-in-loop

我写了一个简单的函数来访问下面数组中的某些值,并且嵌套在数组中的是多个对象。

我的问题与我的2个循环有关。我知道我必须首先遍历数组才能访问3个对象,但是为什么我必须遍历3个对象才能访问值?

基本上,为什么我不能运行初始for循环并通过执行以下操作来获取声音:

animalNoises[i][animal][country]

上面的返回对我来说是未定义的。它与每个3个动物对象的结构方式有关吗?

感谢您的帮助。我真的很感谢堆栈溢出社区的不断帮助。

function petSounds(animal, country) {
let phrase = ''
for (let i = 0; i < animalNoises.length; i++) {
  for (let key in animalNoises[i]){
    if (animal === key){
      let sound = animalNoises[i][key][country];
      phrase = animal + 's' + ' in ' + country + ' say ' + sound
      }
    }
  }
 return phrase
}

    let animalNoises = [
  { 'dog': {
    'America' : 'Woof! Woof!',
    'Germany' : 'Wau Wau!',
    'England' : 'Bow wow!',
    'Uruguay' : 'Jua jua!',
    'Afrikaans' : 'Blaf!',
    'Korea' : 'Mong mong!',
    'Iceland' : 'Voff voff!',
    'Albania' : 'Ham!',
    'Algeria' : 'Ouaf ouaf!'
    }
  },
  { 'cat': {
    'America' : 'Meow',
    'Germany' : 'Miauw!',
    'England' : 'mew mew',
    'Uruguay' : 'Miau Miau!',
    'Afrikaans' : 'Purr',
    'Korea' : 'Nyaong!',
    'Iceland' : 'Kurnau!',
    'Albania' : 'Miau',
    'Algeria' : 'Miaou!'
    }
  },
  { 'chicken': {
    'America' : 'Cluck cluck',
    'Germany' : 'tock tock tock',
    'England' : 'Cluck Cluck',
    'Uruguay' : 'gut gut gdak',
    'Afrikaans' : 'kukeleku',
    'Korea' : 'ko-ko-ko',
    'Iceland' : 'Chuck-chuck!',
    'Albania' : 'Kotkot',
    'Algeria' : 'Cotcotcodet'
    }
  }
];

3 个答案:

答案 0 :(得分:4)

您需要更新json以简化功能(使用以动物类型作为键的对象):

function petSounds(animal, country) {
  const sound = animalNoises[animal][country];
  const phrase = animal + 's' + ' in ' + country + ' say ' + sound;
  return phrase;
}

let animalNoises = {
  'dog': {
    'America': 'Woof! Woof!',
    'Germany': 'Wau Wau!',
    'England': 'Bow wow!',
    'Uruguay': 'Jua jua!',
    'Afrikaans': 'Blaf!',
    'Korea': 'Mong mong!',
    'Iceland': 'Voff voff!',
    'Albania': 'Ham!',
    'Algeria': 'Ouaf ouaf!'

  },
  'cat': {
    'America': 'Meow',
    'Germany': 'Miauw!',
    'England': 'mew mew',
    'Uruguay': 'Miau Miau!',
    'Afrikaans': 'Purr',
    'Korea': 'Nyaong!',
    'Iceland': 'Kurnau!',
    'Albania': 'Miau',
    'Algeria': 'Miaou!'
  },
  'chicken': {
    'America': 'Cluck cluck',
    'Germany': 'tock tock tock',
    'England': 'Cluck Cluck',
    'Uruguay': 'gut gut gdak',
    'Afrikaans': 'kukeleku',
    'Korea': 'ko-ko-ko',
    'Iceland': 'Chuck-chuck!',
    'Albania': 'Kotkot',
    'Algeria': 'Cotcotcodet'
  }
};

console.log(petSounds('cat', 'America'));
console.log(petSounds('dog', 'Iceland'));
console.log(petSounds('chicken', 'Germany'));

答案 1 :(得分:1)

如果要保留现在的表单,可以始终使用Array#find(),然后进行in运算符检查,然后使用模板文字可以轻松创建字符串。

function petSounds(animal, country) {
 const noise = animalNoises.find(obj => animal in obj)[animal][country];
 return `${animal}s in ${country} say ${noise}`
}

    let animalNoises = [
  { 'dog': {
    'America' : 'Woof! Woof!',
    'Germany' : 'Wau Wau!',
    'England' : 'Bow wow!',
    'Uruguay' : 'Jua jua!',
    'Afrikaans' : 'Blaf!',
    'Korea' : 'Mong mong!',
    'Iceland' : 'Voff voff!',
    'Albania' : 'Ham!',
    'Algeria' : 'Ouaf ouaf!'
    }
  },
  { 'cat': {
    'America' : 'Meow',
    'Germany' : 'Miauw!',
    'England' : 'mew mew',
    'Uruguay' : 'Miau Miau!',
    'Afrikaans' : 'Purr',
    'Korea' : 'Nyaong!',
    'Iceland' : 'Kurnau!',
    'Albania' : 'Miau',
    'Algeria' : 'Miaou!'
    }
  },
  { 'chicken': {
    'America' : 'Cluck cluck',
    'Germany' : 'tock tock tock',
    'England' : 'Cluck Cluck',
    'Uruguay' : 'gut gut gdak',
    'Afrikaans' : 'kukeleku',
    'Korea' : 'ko-ko-ko',
    'Iceland' : 'Chuck-chuck!',
    'Albania' : 'Kotkot',
    'Algeria' : 'Cotcotcodet'
    }
  }
];

否则,在您只需要检查是否存在的情况下,您就在循环播放时循环播放。

当然有很多方法可以给猫皮,所以上面的等价于

function petSounds(animal, country) {
 const noise = animalNoises.find(obj => obj.hasOwnProperty(animal))[animal][country];
 return `${animal}s in ${country} say ${noise}`
}

当然,如果您从其他地方接收到此JSON,则可以对其进行简化,然后将键和值关联到超级对象(使用Array#reduce()Object.entries()

animalNoises = animalNoise.reduce((acc, obj) => {
  Object.entries(obj).forEach(([key, value]) => {
   acc[key] = value;
  });
  return acc;
 },
 {}
)

function petSounds(animal, country) {
  return `${animal}s in ${country} say ${animalNoises[animal][country]}`;
}

如果您想了解更多有关使用Array可以完成的有趣工作的信息,请查看MDN for JavaScript Arrays

The in operator是缩短Object#hasOwnProperty()的一种非常有用的方法

And as always a lot more information about JavaScript can be found at the MDN


Object Sestructuring带来了一些额外的乐趣,只是另一种安排事情的方式:

function petSounds(animal, country) {
 const { [animal]: { [country]: noise } } = animalNoises.find(obj => animal in obj);
 return `${animal}s in ${country} say ${noise}`
}

答案 2 :(得分:1)

您的解决方案有效,带有一个for循环。您未指定单引号。 当我简单地控制台它返回特定的值。

animalNoises[0]['dog']['Korea']
"Mong mong!"

在循环中,您需要通过指定键名和国家/地区值来访问数组。

与每个3个动物对象的构造方式无关

当我调用您的函数时,它运行良好。

petSounds('dog', 'Korea')
"dogs in Korea say Mong mong!"

或者您可以如下修改函数,以减少内部循环:

function petSounds(animal, country) {
let phrase = ''
  for (let i = 0; i < animalNoises.length; i++) {
    let key = Object.keys(animalNoises[i])[0];
    if (animal === key){
      let sound = animalNoises[i][key][country];
      phrase = animal + 's' + ' in ' + country + ' say ' + sound
    }
  }
  return phrase
}