如何获取JavaScript对象的所有属性值(不知道键)?


Answers:


447

通过使用一个简单的for..in循环:

for(var key in objects) {
    var value = objects[key];
}

90
请注意要继承的原型对象的属性。请参阅:hasOwnProperty()
橄榄

102
如果你正在读这个答案,你应该明确地阅读对方一个
mgarciaisaia

18
如果您正在阅读此答案,并且可能正在处理字符串,则一定要在表面打孔javascript。

如果您阅读了以上答案,并且想在脸上打JavaScript,请尝试lodash
slugmandrew,

应该指出的是,这将不包括其enumerable标志设置为false的属性。除其他事项外,这意味着您不会迭代任何类方法,但是会迭代以其他方式创建的方法。
rich remer '19

1012

根据您必须支持的浏览器,可以通过多种方式完成此操作。狂野的绝大多数浏览器都支持ECMAScript 5(ES5),但请注意,下面的许多示例都在使用Object.keys,而IE <9中没有这些示例。请参阅兼容性表

ECMAScript 3+

如果必须支持IE的旧版本,则可以选择以下选项:

for (var key in obj) {
    if (Object.prototype.hasOwnProperty.call(obj, key)) {
        var val = obj[key];
        // use val
    }
}

嵌套if可确保您不枚举对象原型链中的属性(这几乎是您肯定想要的行为)。您必须使用

Object.prototype.hasOwnProperty.call(obj, key) // ok

而不是

obj.hasOwnProperty(key) // bad

因为ECMAScript 5+允许您使用创建无原型对象Object.create(null),而这些对象将没有hasOwnProperty方法。顽皮的代码可能还会产生覆盖该hasOwnProperty方法的对象。

ECMAScript 5+

您可以在任何支持ECMAScript 5及更高版本的浏览器中使用这些方法。它们从对象获取值,并避免枚举原型链。obj您的对象在哪里:

var keys = Object.keys(obj);

for (var i = 0; i < keys.length; i++) {
    var val = obj[keys[i]];
    // use val
}

如果您想要一些更紧凑的东西,或者要谨慎使用循环中的函数,那么请Array.prototype.forEach成为您的朋友:

Object.keys(obj).forEach(function (key) {
    var val = obj[key];
    // use val
});

下一个方法将构建一个包含对象值的数组。这对于循环很方便。

var vals = Object.keys(obj).map(function (key) {
    return obj[key];
});

// use vals array

如果您想使那些使用Object.keys安全的设备null(按for-in现状)安全,则可以这样做Object.keys(obj || {})...

Object.keys返回可枚举的属性。对于简单对象的迭代,通常就足够了。如果您需要使用某些具有不可枚举属性的属性,则可以Object.getOwnPropertyNames代替使用Object.keys

ECMAScript 2015+(又名ES6)

使用ECMAScript 2015可以更轻松地迭代数组。在循环中一个接一个地处理值时,可以利用它来发挥优势:

for (const key of Object.keys(obj)) {
    const val = obj[key];
    // use val
}

使用ECMAScript 2015胖箭头功能,将对象映射到值数组成为一种情况:

const vals = Object.keys(obj).map(key => obj[key]);

// use vals array

ECMAScript 2015引入了Symbol,其实例可用作属性名称。要获取要枚举的对象的符号,请使用Object.getOwnPropertySymbols(此功能是为什么Symbol 不能用于制作私有属性的原因)。ReflectECMAScript 2015 的新API提供了Reflect.ownKeys,可返回属性名称(包括不可枚举的属性)和符号的列表。

数组理解(不要尝试使用)

在发布之前,已将数组理解从ECMAScript 6 中删除。在将其删除之前,解决方案应如下所示:

const vals = [for (key of Object.keys(obj)) obj[key]];

// use vals array

ECMAScript 2017+

ECMAScript 2016添加了不影响该主题的功能。ECMAScript 2017规范增加了Object.valuesObject.entries。两个都返回数组(与的类比会让某些人感到惊讶Array.entries)。Object.values可以原样使用或for-of循环使用。

const values = Object.values(obj);

// use values array or:

for (const val of Object.values(obj)) {
    // use val
}

如果要同时使用键和值,则Object.entries适合您。它产生一个充满[key, value]对的数组。您可以按原样使用它,也可以(请注意ECMAScript 2015的解构分配)在for-of循环中使用:

for (const [key, val] of Object.entries(obj)) {
    // use key and val
}

Object.values 匀场

最后,如评论中所述,以及teh_senaus在另一个答案中指出,可能值得将其中之一用作垫片。不用担心,以下内容不会更改原型,它只是向中添加了一种方法Object(危险性要小得多)。使用胖箭头功能,这也可以一行完成:

Object.values = obj => Object.keys(obj).map(key => obj[key]);

您现在可以像

// ['one', 'two', 'three']
var values = Object.values({ a: 'one', b: 'two', c: 'three' });

如果要避免在本机Object.values存在时进行调整,则可以执行以下操作:

Object.values = Object.values || (obj => Object.keys(obj).map(key => obj[key]));

最后...

注意您需要支持的浏览器/版本。以上是实现方法或语言功能的正确位置。例如,直到最近,V8中默认情况下都关闭了对ECMAScript 2015的支持,该功能支持Chrome等浏览器。在打算支持的浏览器实现所需的功能之前,应避免使用ECMAScript 2015的功能。如果使用babel将代码编译为ECMAScript 5,则可以访问此答案中的所有功能。


9
这应该是被接受的(或至少被否决的)答案,因为被接受的答案是不完整的(@olive指出这一点)。
0xc0de 2013年

所有所谓的把戏,我们仍然需要提obj两次,这是可耻的。我想创建一个辅助函数是不可避免的吗?类似于values(obj)。
史蒂文·哈里安托

这些方法中的任何一种都可以用作垫片。例如:Object.values = obj => Object.keys(obj).map(key => obj[key]);
qubyte

1
ECMA 5解决方案应可在所有现代浏览器中使用。ECMA 6尚未最终确定,并且所有浏览器中的支持都是初步的。在Chrome中,部分实施了ECMA 6,但已将其禁用。在Firefox中,支持更好,但是数组理解是错误的(如上所述)。我认为我使用未来时态就暗示了这一点。@JacekLampart,哪个解决方案给您带来错误?
qubyte 2013年

2
我无法想象为什么我们必须等待ES2017获得Object.values()方法。
Herbertusz

31

这是一个可重用的函数,用于将值放入数组。它也考虑了原型。

Object.values = function (obj) {
    var vals = [];
    for( var key in obj ) {
        if ( obj.hasOwnProperty(key) ) {
            vals.push(obj[key]);
        }
    }
    return vals;
}

15
修改Object不是什么大问题(这Object.keys是一个常见的错误),您可能正在考虑修改Object原型。
sandstrom

为什么需要进行测试hasOwnProperty()?在该对象没有属性的循环中如何迭代密钥?
1252748年

4
Google @thomas,这很重要。它可能具有其原型链中的属性。
2014年


14

如果您真的想要一个Values数组,那么我发现比使用for ... in循环构建一个数组更干净。

ECMA 5.1+

function values(o) { return Object.keys(o).map(function(k){return o[k]}) }

值得注意的是,在大多数情况下,您实际上并不需要数组值,这样做会更快:

for(var k in o) something(o[k]);

这将遍历对象o的键。在每次迭代中,将k设置为o的键。


9

ES5 Object.keys

var a = { a: 1, b: 2, c: 3 };
Object.keys(a).map(function(key){ return a[key] });
// result: [1,2,3]

3
为什么这被否决了?我会说这是最干净的解决方案之一。
塞巴斯蒂安·霍亚斯

我不知道,为什么这被否决。这是js中最简单,最纯净的解决方案,无需使用任何库或任何其他实用程序。
sanjeev shetty

5

您可以循环浏览以下按键:

foo = {one:1, two:2, three:3};
for (key in foo){
    console.log("foo["+ key +"]="+ foo[key]);
}

将输出:

foo[one]=1
foo[two]=2
foo[three]=3

2
如果要避免继承属性,还需要检查“ hasOwnProperty()”。
0xc0de 2013年

3

对于CofeeScript时代的早期适应者来说,这是另一种等效方式。

val for key,val of objects

这样做可能会更好,因为objects可以减少再次键入的难度,并降低可读性。

objects[key] for key of objects

3

使用如下所示的polyfill:

if(!Object.values){Object.values=obj=>Object.keys(obj).map(key=>obj[key])}

然后使用

Object.values(my_object)

3)赢利!



2

显然-正如我最近所了解的-这是最快的方法:

var objs = {...};
var objKeys = Object.keys(obj);
for (var i = 0, objLen = objKeys.length; i < objLen; i++) {
    // do whatever in here
    var obj = objs[objKeys[i]];
}

您可以将Codepen或jsfiddle用作示例吗?谢谢。
克里斯22年

2

这个问题没有指定是否还需要继承和不可枚举的属性。

还有一个问题,要获取 Google无法轻易找到的所有内容,继承的属性和不可枚举的属性

我的解决方案是:

function getAllPropertyNames(obj) {
    let result = new Set();
    while (obj) {
        Object.getOwnPropertyNames(obj).forEach(p => result.add(p));
        obj = Object.getPrototypeOf(obj);
    }
    return [...result];
}

然后遍历它们,只需使用for-of循环:


1

使用: Object.values(),我们传入一个对象作为参数,并接收一个值数组作为返回值。

这将返回给定对象自己的可枚举属性值的数组。您将获得与使用for in循环相同的值,但没有原型上​​的属性。这个例子可能会使事情更清楚:

function person (name) {
  this.name = name;
}

person.prototype.age = 5;

let dude = new person('dude');

for(let prop in dude) {
  console.log(dude[prop]);     // for in still shows age because this is on the prototype
}                              // we can use hasOwnProperty but this is not very elegant

// ES6 + 
console.log(Object.values(dude));
// very concise and we don't show props on prototype


1
const object1 = {
  a: 'somestring',
  b: 42
};

for (let [key, value] of Object.entries(object1)) {
  console.log(`${key}: ${value}`);
}

// expected output:
// "a: somestring"
// "b: 42"
// order is not guaranteed

0

这是类似于PHP的array_values()的函数

function array_values(input) {
  var output = [], key = '';
  for ( key in input ) { output[output.length] = input[key]; }
  return output;
}

如果您使用的是ES6或更高版本,请按以下方法获取对象的值:

Array.from(values(obj));

由于某些原因,values()在Chrome和Firefox中可以使用,但在iojs / node上则不能。
jaggedsoft

0

甚至与某些浏览器不兼容的ES7

由于,Object.values(<object>)将内置于ES7

在等待所有浏览器支持它之前,您可以将其包装在一个函数中:

Object.vals=(o)=>(Object.values)?Object.values(o):Object.keys(o).map((k)=>o[k])

然后 :

Object.vals({lastname:'T',firstname:'A'})
 // ['T','A']

浏览器与ES7兼容后,您将无需更改代码中的任何内容。


0

我知道我来晚了一点,但这是新的Firefox 47 方法的补片Object.values

Object.prototype.values = Object.prototype.values || function(obj) {
  return this.keys(obj).map(function(key){
    return obj[key];
  });
};

0

Object.entries以更好的方式做到这一点。

  var dataObject = {"a":{"title":"shop"}, "b":{"title":"home"}}
 
   Object.entries(dataObject).map(itemArray => { 
     console.log("key=", itemArray[0], "value=", itemArray[1])
  })


0

const myObj = { a:1, b:2, c:3 }

获取所有值:

  • 最短的方法:

    • const myValues = Object.values(myObj)
  • const myValues = Object.keys(myObj).map(key => myObj[key])


-1
var objects={...}; this.getAllvalues = function () {
        var vls = [];
        for (var key in objects) {
            vls.push(objects[key]);
        }
        return vls;
    }

-5

ECMAScript5中使用

 keys = Object.keys(object);

否则,如果您的浏览器不支持它,请使用众所周知的 for..in loop

for (key in object) {
    // your code here
}

17
问题是要求输入值,而不是键。
zachelrath 2012年

@zachelrath你是对的。-但是,如果您想获取值,则此脚本很有用,因为当您知道键时,便可以使用它object[key]来循环获取值。
fridojet 2012年

2
@fridojet但这可以for..in(和hasOwnProperty)完成,所以它实际上并没有获得任何收益..我希望ECMAScript 5th可以定义Object.pairs(并且Object.items用于[[key, value], ..]),但是可惜没有。
user2246674

-8

现在,我使用Dojo Toolkit,因为旧的浏览器不支持Object.values

require(['dojox/lang/functional/object'], function(Object) {
    var obj = { key1: '1', key2: '2', key3: '3' };
    var values = Object.values(obj);
    console.log(values);
});

输出:

['1', '2', '3']

5
严格来说,数组是不正确的。您有一个字符串数组,而不是数字数组。
qubyte

-10

采用

console.log(variable)

如果您使用的是Google Chrome浏览器,请使用Ctrl + Shift + j打开控制台

转到>>控制台

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.