如果未定义,则未设置键值对,但具有默认值



我有一个具有各种键值的对象(简化):

const params = {
dev: {
api: {},
iot: {},
},
test: {
api: {},
iot: {},
}
};

我想通过Object.keys().forEach函数填充:

Object.keys(params).forEach(key => {
params[key].iot.keyName = `/firstURL/`;
params[key].api.anotherKeyName = `/url/var2`;
});

目前,这按预期填充,但是如果我从参数对象中删除密钥(API/IOT),则会出现undefined错误。

我的想法是检查是否首先定义了键,如果没有(实际上永远不会),请使用默认值:

Object.keys(params).forEach(key => {
params[key].iot.keyName = params[key].iot.keyName || `/firstURL/`;
params[key].api.anotherKeyName = params[key].api.anotherKeyName || `/url/var2`;
});

我从params对象中删除键的原因是,它们总是动态生成的(取决于您所处的环境)。

为什么当我检查它是否存在时,我会收到一个未定义keyName错误,如果不存在,请为其分配一个值?

非常感谢。

目前,它会按预期填充,但是如果我从 params 对象中删除密钥 (API/IOT),我会收到一个未定义的错误。

(我的强调)

答案是肯定的。您的代码不会以任何方式检查以确保它们首先存在。为此:

Object.keys(params).forEach(key => {
if (params[key].iot) params[key].iot.keyName = `/firstURL/`;
if (params[key].api) params[key].api.anotherKeyName = `/url/var2`;
});

旁注:您可能会查看Object.values,在 ES2017 中添加但完全可填充:

Object.values(params).forEach(entry => {
if (entry.iot) entry.iot.keyName = `/firstURL/`;
if (entry.api) entry.api.anotherKeyName = `/url/var2`;
});

为什么当我检查它时,我会收到一个keyName未定义的错误 存在,如果不存在,请为其赋值?

您没有收到keyNameundefined的消息。如果您仔细观察,消息上会显示Cannot read property 'keyName' of undefined".

const params = {
dev: {},
test: {}
};
Object.keys(params).forEach(key => {
params[key].iot.keyName = params[key].iot.keyName || `/firstURL/`;
params[key].api.anotherKeyName = params[key].api.anotherKeyName || `/url/var2`;
});

这不是在抱怨keyName.它抱怨您无法在其他undefined的东西上读取该属性 - 某些东西iot.

您正在检查keyName是否存在,如果不存在,则为其设置默认值,但这不是问题所在。问题是iot不存在。


收到错误是因为,虽然您只需为其赋值即可创建新属性,但无法访问不存在的属性上的属性,这就是您正在执行的操作:

params[key].iot.keyName = `/firstURL/`;

如果iot不存在,则无法访问iot.keyName

举例说明:

var obj = {};
obj.key1 = "foo";        // works
obj.key2.subKey = "bar"; // fails because key2 doesn't exist so bar can't be created on it

在访问属性的属性之前,需要添加一些检查以查看属性是否存在。下面是一个示例:

var obj = {};
obj.key1 = "foo";        // works
if(obj.key2){
obj.key2.subKey = "bar"; // works when key2 exists
} else {
obj.key2 = {};           // Create the key
obj.key2.subKey = "bar"; // Now, you can access it and make sub-keys
}
console.log(obj);

一个简单的思考方法是用几代人的类比。

  • params是第一代
  • iot是第二代(params的孩子)
  • keyName是第三代(iot的孩子和一个孙子 的params)

就像在现实世界中一样,如果您没有孩子,您就不能照顾孙子孙女。儿童必须排在第一位。当还没有子代时,您的代码会尝试与孙子一起工作。

最新更新