【问题标题】:arr.splice index inserts in all available indexesarr.splice 索引插入所有可用索引
【发布时间】:2020-10-20 10:32:19
【问题描述】:
        const list = []
        const obj = {
          name: '',
          mobile: ''
        }
        _.forEach(errors, (value, key) => {
          // eslint-disable-next-line no-debugger
          // debugger
          const field = key.split('.')[2]
          const index = key.split('.')[1]
          obj[field] = value[0]
          list.splice(index, 1, obj)
          console.log(obj)
        })

上面是我正在处理的代码。下面是每个obj 变量的日志截图

我想要的是将该对象插入到 list 变量的 index 中。

但循环完成后我得到的是

循环中的最后一项会覆盖list 数组中的所有内容。

顺便说一下index

总而言之,我需要将obj 插入到list 数组中的特定index

编辑

errors 变量如下所示

我需要它看起来像这样。

list = [
   { name: 'name error message here', mobile: 'error message here' },
   { name: 'name error message here', mobile: 'error message here' },
   { name: 'name error message here', mobile: 'error message here' },
   { name: 'name error message here', mobile: 'error message here' }
]

【问题讨论】:

  • "总而言之,我需要将 obj 插入到列表数组中的特定索引中。" 那你不应该只做list[index] = obj 吗?
  • @3limin4t0r 我正在用 obj[field] = value[0] 替换该值。如果我在 foreach 中实例化 obj,前三个名称将消失。
  • @VLAZ 我这样做了,但它与拼接的行为方式相同。
  • 这个问题或许可以简化。 errors 是什么样的(即输入),您希望输出是什么样的?
  • @BenAston 我会更新问题。

标签: javascript vue.js nuxtjs


【解决方案1】:

这是你想要的吗?

function transform(data) {  
  return Object.entries(data).reduce((p, [key, [message]]) => {
    const keyElements = key.split('.')
    p[keyElements[1]] = p[keyElements[1]] || {}
    p[keyElements[1]][keyElements[2]] = message
    return p
  }, [])
}

const data = {
  'contacts.0.mobile': ["Error. Mobile number is a required field."],
  'contacts.0.name': ["Error. Contact name is a required field."],
  'contacts.1.mobile': ["Error. Mobile number is a required field."],
  'contacts.1.name': ["Error. Contact name is a required field."]
}
console.log(transform(data))

或者使用正则表达式和命名的捕获组:

   
const PATTERN = /contacts.(?<index>\d+).(?<type>\w+)/

function transform(data) {  
  return Object.entries(data).reduce((p, [key, [message]]) => {
    const { index, type } = PATTERN.exec(key).groups
    p[index] = p[index] || {}
    p[index][type] = message
    return p
  }, [])
}

const data = {
  'contacts.0.mobile': ["Error. Mobile number is a required field."],
  'contacts.0.name': ["Error. Contact name is a required field."],
  'contacts.1.mobile': ["Error. Mobile number is a required field."],
  'contacts.1.name': ["Error. Contact name is a required field."]
}
console.log(transform(data))

【讨论】:

  • 请问p[index] = p[index] || {}是什么意思
  • 如果该索引处尚不存在对象,则添加一个。
【解决方案2】:

问题是您在forEach 循环之外创建obj 并为errors 中的所有元素插入相同的obj。如果您随后更新obj,您将更新所有元素,因为所有元素都是对同一对象的引用。如果您希望每个 index 都有自己的对象,您应该在代码中反映这一点。

const errors = {
  "contacts.0.mobile": ["Error. Mobile number is a required field."],
  "contacts.0.name":   ["Error. Contact name is a required field." ],
  "contacts.1.mobile": ["Error. Mobile number is a required field."],
  "contacts.1.name":   ["Error. Contact name is a required field." ],
};

const list = [];
_.forEach(errors, (value, key) => {
  const [, index, field] = key.split(".");
  if (!list[index]) list.splice(index, 1, {name: "", mobile: ""});
  list[index][field] = value[0];
});

console.log(list);
&lt;script src="https://cdn.jsdelivr.net/npm/lodash@4.17.20/lodash.min.js"&gt;&lt;/script&gt;

上面将为遇到的每个新index 创建一个新对象。

【讨论】:

  • 哦。我现在明白了,但是当我尝试这个时,我只得到了“移动”字段及其值,而“名称”字段被覆盖了。我该如何解决这个问题?
  • @Lucentyr 要回答这个问题,我必须知道errors 的内容是什么以及预期的list 结果是什么。所以我无法用提供的信息回答这个问题。
  • 我用errors 的内容和list 所需的输出更新了问题。
  • 用你更新的评论,我只得到名称值。
  • @Lucentyr 我不完全确定你的意思,我已将代码块更改为 sn-p,它似乎运行得很好。
猜你喜欢
  • 2011-09-22
  • 2010-09-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-10-06
  • 1970-01-01
  • 2016-11-26
相关资源
最近更新 更多