【问题标题】:Javascript Array doesn't map correctlyJavascript 数组未正确映射
【发布时间】:2020-12-13 11:34:15
【问题描述】:

我正在“安慰”整个代码......但我找不到任何问题,只有一个奇怪的行为。

让我解释一下: 我有一个角度组件(我们称之为 parent),它通过 inputTags 向他的 child 发送一些 tags大批。 然后我需要设置另一个包含用户所有标签的列表,称为 allTags

数组(inputTagsallTags)的格式如下: { id:'tagId',名称:'tagName' }

我需要将这两者组成一个统一的数组。预期的输出应包含其格式如下的项目数组:{ id: 'tagId', name: 'tagName', selected: boolean }

为了做到这一点,我以这种方式映射 allTags 数组:

让我们假设:

inputTags = [
    { id: 'work', name: 'Work' },
    { id: 'motivation', name: 'Motivation' }
];

allTags = [
    { id: 'network', name: 'Network' },
    { id: 'work', name: 'Work' },
    { id: 'smart', name: 'Smart' },
    { id: 'motivation', name: 'Motivation' }
];

现在... allTags 实际上是从服务器检索的,所以我的代码如下所示:

this.tagsService.getAll().subscribe(tags => {

    this.allTags = tags.map(tag => {
        let select = false;
        this.inputTags.forEach(inputTag => { select = (inputTag.id === tag.id) })
        return {
          id: tag.id,
          name: tag.name,
          selected: select,
        };      
    });

})

这对我来说似乎很标准,但实际上不是,因为不是得到:

allTags = [
    { id: 'network', name: 'Network', selected: false },
    { id: 'work', name: 'Work', selected: true }, // is selected
    { id: 'smart', name: 'Smart', selected: false },
    { id: 'motivation', name: 'Motivation', selected: true } // is selected
];

我明白了:

allTags = [
    { id: 'network', name: 'Network', selected: false },
    { id: 'work', name: 'Work', selected: false }, // is NOT selected
    { id: 'smart', name: 'Smart', selected: false },
    { id: 'motivation', name: 'Motivation', selected: true } // is selected
];

基本上问题是它只选择一个标签,而不是多个标签。

【问题讨论】:

  • .forEach() 是错误的。您只会得到列表中最后一个元素的“id”比较结果,因为select 每次都会无条件更新。

标签: javascript arrays angular


【解决方案1】:

你可以试试some:

this.allTags = tags.map(tag => {
    return {
      id: tag.id,
      name: tag.name,
      selected: this.inputTags.some(inputTag => inputTag.id === tag.id)
    };      
});

【讨论】:

  • 它有效,谢谢!使用 Santi Barbat 回复,使用“find()”和三元运算符,还是你的更好?
  • @PietroLungarini 都是正确的,但这个更短
【解决方案2】:

JavaScript Array map() 方法

*) 使用为每个数组元素调用函数的结果创建一个新数组,并按顺序为数组中的每个元素调用一次提供的函数。

注意:map() 方法不会对没有值的数组元素执行函数,也不会改变原始数组。

【讨论】:

    【解决方案3】:

    尝试以下方法:

    this.allTags = allTags.map(tag => ({
      id: tag.id,
      name: tag.name,
      selected: inputTags.some(i => i.id === tag.id),
    }))
    

    【讨论】:

    • 它有效,谢谢!使用 Amadou Beye 回复,使用“some()”还是你的更好?
    • 两者的结合,使用some(),但没有像我的那样返回:)
    猜你喜欢
    • 2020-08-02
    • 2021-02-04
    • 1970-01-01
    • 1970-01-01
    • 2016-10-05
    • 1970-01-01
    • 1970-01-01
    • 2015-07-18
    • 2014-03-04
    相关资源
    最近更新 更多