【问题标题】:Compare and process booleans in an object比较和处理对象中的布尔值
【发布时间】:2020-01-02 06:32:14
【问题描述】:

我遇到的问题是我有一组相同的对象,看起来像:

[
    {
        error:null,
        permissions:{ 
            perm1:false,
            perm2:true,
            perm3:false,
            etc...
        }
    },
    {
        error:null,
        permissions:{ 
            perm1:true,
            perm2:false,
            perm3:false,
            etc...
        }
    },
    {
        error:null,
        permissions:{ 
            perm1:false,
            perm2:false,
            perm3:false,
            etc...
        }
    },
    etc..
]

我需要做的是将所有这些“添加”在一起并得到类似的东西:

{
    error:null,
    permissions:{ 
        perm1:true,
        perm2:true,
        perm3:false,
        etc...
    }
}

我想到了这段代码:

var newObj = {};

for(myObject in objectArray){
    for(var [key, value] of Object.entries(myObject)){
        newObj[key] = (newObj[key] === true ? true : value)
    }
}

return newObj;

但这似乎并不真正有效(或者它会起作用......),我需要最有效和最快速的方法。如果您能指出我正确的方向,或者将我链接到可能对我有帮助的问题。

【问题讨论】:

  • error 怎么样,它会一直是null,或者你希望新对象有什么?
  • 最大的问题是我从另一个函数中获取这些对象,如果其中任何一个失败,联系人和 API 来获取数据,错误就会存储在那里,这意味着如果错误!== null 我们应该退出,然后返回错误。编辑:实际上现在考虑它,我们可以忽略它。新对象不需要它,因为我在对象被扔进数组之前对它们进行了几次检查!

标签: javascript arrays performance loops


【解决方案1】:

如果所有对象中的键都相同,则可以取一个对象键的数组,然后遍历每个键并通过检查对象的.some 是否具有确实如此:

const arr = [
    {
        error:null,
        permissions:{ 
            perm1:false,
            perm2:true,
            perm3:false,
        }
    },
    {
        error:null,
        permissions:{ 
            perm1:true,
            perm2:false,
            perm3:false,
        }
    },
    {
        error:null,
        permissions:{ 
            perm1:false,
            perm2:false,
            perm3:false,
        }
    },
];
const errorObj = arr.find(({ error }) => error);
if (errorObj) {
  throw new Error(errorObj.error);
}
const keys = Object.keys(arr[0].permissions);
const permissions = Object.fromEntries(keys.map(
  key => [key, arr.some(({ permissions }) => permissions[key])]
));
console.log({ error: null, permissions });

可能会进行一些优化,在某些情况下可能是值得的,但这基本上是一个 O(n^2) 操作,最重要的事情是将属性短路到 true找到匹配项,而不是继续通过数组的其余部分,.some 完成。

【讨论】:

    【解决方案2】:

    请试试这个

    var objectArray=[
        {
            error:null,
            permissions:{ 
                perm1:false,
                perm2:true,
                perm3:false
            }
        },
        {
            error:null,
            permissions:{ 
                perm1:true,
                perm2:false,
                perm3:false
            }
        },
        {
            error:null,
            permissions:{ 
                perm1:false,
                perm2:false,
                perm3:false
            }
        }
    ]
    
    
    var newObj = null;
    
    for(myObject in objectArray){
        let x=objectArray[myObject]
        if(newObj===null){
          newObj=x;
        }else{
          Object.keys(x.permissions).map(i=>{
             if(!newObj.permissions[i]){
              newObj.permissions[i]=x.permissions[i];
             }
          })
        }
    }
    
    console.log(newObj)

    【讨论】:

      【解决方案3】:

      您可以将.reduce() 与数组中的第一个对象一起用作累加器。对于数组中的每个对象,您可以遍历累加器权限中的键,并根据当前对象的值是否为 true 来更改其 true/false 值:

      const arr = [{ error: null, permissions: { perm1: false, perm2: true, perm3: false, } }, { error: null, permissions: { perm1: true, perm2: false, perm3: false, } }, { error: null, permissions: { perm1: false, perm2: false, perm3: false, } } ];
      
      const [{error, permissions: p}] = arr;
      const res = arr.reduce((acc, {permissions}) => {
        for(const key in acc.permissions)
          acc.permissions[key] = acc.permissions[key] || permissions[key];
        return acc;
      }, {error, permissions: {...p}});
      
      console.log(res);

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2013-05-22
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多