如何在 JavaScript 中的另一个对象中找到带有 属性 的对象

How do I find objects with a property inside another object in JavaScript

我有一个包含所有用户的对象,如下所示:var users = {user1:{}, user2:{}},并且每个用户都有一个正在播放 属性。我如何获得所有 isPlaying 错误的用户?

您应该使用 Object.keysArray.prototype.filterArray.prototype.map:

// This will turn users object properties into a string array
// of user names
var userNames = Object.keys(users);

// #1 You need to filter which users aren't playing. So, you
// filter accessing users object by user name and you check that
// user.isPlaying is false
//
// #2 Using Array.prototype.map, you turn user names into user objects
// by projecting each user name into the user object!
var usersNotPlaying = userNames.filter(function(userName) { 
   return !users[userName].isPlaying; 
}).map(function(userName) {
   return users[userName];
});

如果使用 ECMA-Script 6 可以完成,则可以使用箭头函数:

// Compact and nicer!
var usersNotPlaying = Object.keys(users)
                       .filter(userName => users[userName].isPlaying)
                       .map(userName => users[userName]);

使用Array.prototype.reduce

正如@RobG 所指出的,您也可以使用 Array.prototype.reduce

虽然我不想重叠他的新答案和自己的答案,但我相信 reduce 方法更实用,如果 return 是一个用户对象数组 不是播放.

基本上,如果您 return 对象而不是数组,问题是另一个调用者(即调用执行所谓 reduce 的函数的函数)可能需要调用reduce 再次执行新操作,而数组已经准备好流畅地调用其他 Array.prototype 函数,如 mapfilterforEach...

代码看起来像这样:

// #1 We turn user properties into an array of property names
// #2 Then we call "reduce" on the user property name array. Reduce
//    takes a callback that will be called for every array item and it receives
//    the array reference given as second parameter of "reduce" after 
//    the callback.
// #3 If the user is not playing, we add the user object to the resulting array
// #4 Finally, "reduce" returns the array that was passed as second argument
//    and contains user objects not playing ;)
var usersNotPlaying = Object.keys(users).reduce(function (result, userName) {
    if (!users[userName].isPlaying) 
        result.push(users[userName]);
    return result;
}, []); // <-- [] is the new array which will accumulate each user not playing

显然使用 Array.prototype.reducemapfilter 集中在一个循环中,在大数组中,reduce 应该优于 "filter+map" 方法,因为循环一个大数组两次过滤不玩游戏的用户并再次循环将他们再次映射到对象可能很重...

总结:当我们谈论很少的项目时,我仍然会使用 filter+map 而不是 reduce,因为有时 readability/productivity比优化更重要,在我们的例子中,filter+map 方法似乎比 reduce 需要更少的解释(自文档化代码!)。

无论如何,readability/productivity 取决于谁进行实际编码...

遍历您的用户对象:

var list = [];
for (var key in users) {
    if (users[key].isPlaying === false) {
        list.push(key);
    }
}

这将为您提供 isPlaying 属性 为 false.

的所有用户的列表

如果您想要 isPlaying 为 false 的所有用户对象,您可以自己添加对象:

var list = [];
for (var key in users) {
    if (users[key].isPlaying === false) {
        list.push(users[key]);
    }
}

请尝试以下 JS 代码:将所有 isPlaying 设置为 false。

var json_object={};//{"user1":{"isPlaying":"false"},"user2":{"isPlaying":"ture"}};
json_object['user1']={"isPlaying":"false"};
json_object['user2']={"isPlaying":"ture"};
console.log(json_object); 
for(var key in json_object){
    if(json_object[key].isPlaying === "false"){/*do what you want*/}
}
console.log(json_object);

这也可以使用 Array.prototype.reduce 来实现,这是一个非常全面的工具。它从获取名称数组开始:

var userNames = Object.keys(users);

到 return 数组只是用户名,其中 isPlaying 是假的,你可以这样做:

var usersNotPlaying = userNames.reduce(function(names, name) {
                        if (!users[name].isPlaying) {
                          names.push(name);
                        }
                        return names}, []);

到return一个对象的用户对象以他们的名字作为键是相似的:

var usersNotPlaying = userNames.reduce(function(names, name) {
                        if (!users[name].isPlaying) {
                          names[name] = users[name];
                        }
                        return names}, {});

您也可以以类似的方式使用 forEach,但是因为它 returns undefined 对象或数组收集成员必须首先在外部范围内初始化:

var usersNotPlaying = {};
userNames.forEach(function(name) {
  if (!users[name].isPlaying) {
    usersNotPlaying[name] = users[name];
  }
});

你也可以使用for..in:

var usersNotPlaying = {};
for (var user in users) {
  if (users.hasOwnProperty(user) && !users[user].isPlaying) {
    usersNotPlaying[user] = users[user];
  }
}

以上都可以 return 名称数组、用户对象数组或用户对象对象。选择适合的。 ;-)