如何以数组元素命名对象属性?为何map返回结果不符预期?
嘿,我来帮你把这两个问题掰扯清楚,都是ES6对象语法里的常见坑点:
问题1:如何创建以数组元素命名属性的对象?
你可以用ES6的计算属性名或者Object.fromEntries来实现,分两种场景:
如果是单个变量生成属性:
用中括号把变量包起来,告诉JS要拿变量的值当属性名,而不是变量的字面名称:const userName = 'Adam'; const userObj = { [userName]: {} }; console.log(userObj); // { Adam: {} }如果是批量从数组生成:
用Object.fromEntries配合map最简洁,把数组元素转换成[键名, 属性值]的格式,再组装成对象:const names = ['Adam', 'Eva']; const userMap = Object.fromEntries(names.map(name => [name, {}])); console.log(userMap); // { Adam: {}, Eva: {} }如果你习惯用
reduce手动构建,也可以这么写:const names = ['Adam', 'Eva']; const userMap = names.reduce((acc, name) => { acc[name] = {}; return acc; }, {}); console.log(userMap); // { Adam: {}, Eva: {} }
问题2:为什么map回调里的
({man})不会生成变量名作为键? 这是因为你混淆了对象属性简写的作用场景:
当你写let Adam = {}; {Adam}时,这里的{Adam}是ES6的属性简写语法,等价于{Adam: Adam}——这里的键是当前作用域中变量Adam的字面名称,值是变量Adam的内容。
但在[Adam, Eva].map(man => ({man}))里,回调函数是一个独立的作用域,参数man只是个占位符:不管你传进去的是Adam还是Eva,在回调内部它都叫man,所以({man})等价于{man: man},属性键固定为字符串'man',JS根本不知道外部传入的变量原本叫什么名字。
如果想要在map里生成以原变量名作为键的对象,你需要先把变量和它的名字配对(比如放进二维数组),再用计算属性名:
let Adam = {}; let Eva = {}; // 先把变量名和变量本身配对 const people = [['Adam', Adam], ['Eva', Eva]]; const result = people.map(([name, obj]) => ({ [name]: obj })); console.log(result); // [ { Adam: {} }, { Eva: {} } ]
内容的提问来源于stack exchange,提问作者anthnyprschka
相关产品推荐
相关产品推荐

