ChatGPT解决这个技术问题 Extra ChatGPT

JavaScript 中的 For..In 循环 - 键值对

我想知道是否有办法在 JavaScript 中执行类似 PHP foreach 循环的操作。我正在寻找的功能类似于这个 PHP Snippet:

foreach($data as $key => $value) { }

我正在查看 JS for..in 循环,但似乎无法指定 as。如果我使用“正常”for循环(for(var i = 0; i < data.length; i++)执行此操作,有没有办法抓住关键=>价值对?


M
Michael Levy
for (var k in target){
    if (target.hasOwnProperty(k)) {
         alert("Key is " + k + ", value is " + target[k]);
    }
}

hasOwnProperty 用于检查您的 target 是否真的具有该属性,而不是从其原型继承它。更简单的是:

for (var k in target){
    if (typeof target[k] !== 'function') {
         alert("Key is " + k + ", value is" + target[k]);
    }
}

它只是检查 k 不是方法(就像 targetarray 一样,您会收到很多方法警报,例如 indexOfpushpop 等)


仅对“自己的”属性进行迭代的另一种方法是 Object.keysObject.keys(target).forEach(function (key) { target[key]; });
如果使用 Object.create(null) 创建 target 将无法工作,应更改代码 target.hasOwnProperty(k) -> Object.prototype.hasOwnProperty.call(target,k)
为什么不使用问题示例中给出的变量? ktargetproperty 是什么?对我来说,非javascripter这个未定义的领域:)
Object.keys(target).forEach((key) => { target[key]; });对于角
我想说的是,几乎每次你看到 obj.hasOwnProperty(k) 时,它都应该被重写为 Object.prototype.hasOwnProperty.call(obj, k)。如果您不知道一个对象是否有自己的属性 k,那么您可能也不知道肯定它是否有一个名为 "hasOwnProperty" 的自己的属性;如果是这样,你不想要那个,你想要来自 Object.prototype 的那个。因此,IMO 将 hasOwnProperty 作为一种方法根本就是语言的设计缺陷;没有人希望它的行为在实践中被覆盖。
M
Muhammad Dyas Yaskur

如果您可以本机使用 ES6 或与 Babel(js 编译器)一起使用,那么您可以执行以下操作:

常量测试 = {a: 1, b: 2, c: 3}; for (const [key, value] of Object.entries(test)) { console.log(key, value); }

这将打印出这个输出:

a 1
b 2
c 3

Object.entries() 方法返回给定对象自己的可枚举属性 [key, value] 对的数组,其顺序与 for...in 循环 提供的顺序相同(不同之处在于 for-in 循环枚举原型链中的属性)

Object.entries 文档

对于...的文档

解构分配文档

属性文档的可枚举性和所有权


这很完美,只是想知道 - 与“for key in object 然后通过 object[key] 获取值”相比,哪一个提供更好的性能?
在这种特定情况下,我会假设它会因为 Object.entries 调用而变慢。虽然我没有进行任何测试。
这是手头问题的最佳答案,该问题询问如何在 for 循环中同时获取键和值。
接受的答案应该更新,因为这实际上回答了问题,尽管它在问题发生时不可用。
您可能想检查这个问题:stackoverflow.com/questions/47213651/… 这似乎表明建议使用这种类型的语法: Object.keys(myObject).forEach(key => {...
A
Afshin Moazami

没有人提到 Object.keys,所以我会提到它。

Object.keys(obj).forEach(function (key) {
   // do something with obj[key]
});

注意:IE8 及以下不支持。
此时您应该使用 ES5 垫片。如果您生活在美好的 ES6 未来,请使用 for of tc39wiki.calculist.org/es6/for-of
值得注意的是,“除了抛出异常之外,没有其他方法可以停止或中断 forEach() 循环”
Object.keys(obj).forEach((key) => { });对于角
它在 ES6 上不起作用,或者我不明白。 Felix 在下面有一个更好、更易读的答案: data.forEach(function(value, index) { console.log(index); // 0 , 1, 2... });
P
Paul

for...in 将为您工作。

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

在现代 JavaScript 中,你也可以这样做:

for ( const [key,value] of Object.entries( obj ) ) {

}

J
JD.
var obj = {...};
for (var key in obj) {
    var value = obj[key];

}

php 语法只是糖。


这也将迭代所有继承的属性。为避免这种情况,请使用 .hasOwnProperty()。
F
Felix Kling

我假设您知道 i 是键,并且您可以通过 data[i] 获取值(并且只想要一个快捷方式)。

ECMAScript5 为数组引入了 forEach [MDN](看起来你有一个数组):

data.forEach(function(value, index) {

});

MDN 文档为不支持它的浏览器提供了一个 shim。

当然这对对象不起作用,但你可以为它们创建一个类似的函数:

function forEach(object, callback) {
    for(var prop in object) {
        if(object.hasOwnProperty(prop)) {
            callback(prop, object[prop]);
        }
    }
}

由于您使用 标记了问题,因此 jQuery 提供了 $.each [docs] 循环遍历数组和对象结构。


那是数组 forEach,而不是对象 forEach
所以?显然 OP 正在遍历一个数组。
Mozilla(Firefox、SpiderMonkey-C、Rhino 和 c)还有一个允许 for each 语法的非标准扩展。 for each (let val in myObj) console.log(val);
@katspaugh:是的,但由于它只是 Mozilla,它似乎不是很有用。
非常感谢您的回答。我会阅读你提供的信息。您在答案开始时的假设是正确的,我知道这一点,除了我对这个项目有太多的想法,以至于我无法集中注意力并忘记了它。谢谢。
C
Christoph Winkler

为此,您可以使用 for..in

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

S
Siddhu
for (var key in myMap) {
    if (myMap.hasOwnProperty(key)) {
        console.log("key =" + key);
        console.log("value =" + myMap[key]);
    }
}

在 javascript 中,每个对象都有一堆具有元信息的内置键值对。当您遍历对象的所有键值对时,您也在遍历它们。使用 hasOwnProperty() 过滤掉这些。


T
Tonatio

有三个选项可以处理对象的键和值:

选择值: Object.values(obj).forEach(value => ...);选择键: Object.keys(obj).forEach(key => ...);选择键和值: Object.entries(obj).forEach(([key, value]) => ...);


i
ife
let test = {a: 1, b: 2, c: 3};
Object.entries(test).forEach(([key, value]) => console.log(key, value))

// a 1
// b 2
// c 3

您可以在发布的代码中添加一些解释,而不是发布可能无法理解的纯代码。
Object.entries 根据原始对象的键/值对拉出一个数组数组:[['a', 1],['b',2],['c',3]]forEach 解构每个键/值数组并将两个变量设置为 keyvalue,以便在 in 函数中使用 - 这里是 console.log 中的输出。
D
David

在提出这个问题后的最后几年里,Javascript 增加了一些新特性。其中之一是 Object.Entries 方法。

直接从MDN复制的是以下代码片段


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

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

S
Stephen Murby

ES6 将提供 Map.prototype.forEach(callback) 可以像这样使用

myMap.forEach(function(value, key, myMap) {
                        // Do something
                    });

参数 myMap 是干什么用的?
地图不是对象。它们是完全不同的东西。
forEach 函数不包含数组的“键”,而是包含您当前正在迭代的元素的索引。
R
Richard Dalton

您可以为此使用“for in”循环:

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

A
Aidamina

下面是一个尽可能接近的示例。

for(var key in data){
  var value = data[key];    
  //your processing here
}

如果您使用 jQuery,请参阅:http://api.jquery.com/jQuery.each/


G
Gil Epshtain

如果您使用 Lodash,则可以使用 _.forEach

_.forEach({ 'a': 1, 'b': 2 }, function(value, key) {
  console.log(key + ": " + value);
});
// => Logs 'a: 1' then 'b: 2' (iteration order is not guaranteed).

g
gros chat

为什么不简单地这个

var donuts = [
{ type: "Jelly", cost: 1.22 },
{ type: "Chocolate", cost: 2.45 },
{ type: "Cider", cost: 1.59 },
{ type: "Boston Cream", cost: 5.99 }];

donuts.forEach(v => {console.log(v["type"]+ " donuts cost $"+v["cost"]+" each")});

为什么不包括教育解释? OP 想要从一维结构中获取键和值——你的答案是忽略这个要求。
N
Nazmul Haque

请尝试以下代码:

<script> 
 const games = {
  "Fifa": "232",
  "Minecraft": "476",
  "Call of Duty": "182"
 };

Object.keys(games).forEach((item, index, array) => {
  var msg = item+' '+games[item];
  console.log(msg);
});

如果您不使用它,为什么会出现 array?与 5 年前的相同建议相比,您的回答有何价值?
A
Alex Pacurar

是的,您也可以在 javascript 中使用关联数组:

var obj = 
{
    name:'some name',
    otherProperty:'prop value',
    date: new Date()
};
for(i in obj)
{
    var propVal = obj[i]; // i is the key, and obj[i] is the value ...
}

@PaulPRO ... javascript 中的所有内容都是键值对(因此,对象实际上是键值对的关联数组...)
@AlexPacurar 和关联数组有一个顺序。一个对象是无序的。那是一个很大的区别
@Raynos你可能是对的......这将有助于准确解释一个对象是如何无序的......鉴于上面的例子,人们会期望for循环中的'i'是[name,otherProperty,最后是日期]...那么在什么情况下对象的属性顺序会混合?
@AlexPacurar 循环对象的特定顺序是特定于浏览器的。有些是按字母顺序做的,有些是按定义顺序做的,等等
@Raynos:关联数组是否必须有序?我经常看到这个词被更广泛地使用。例如,在 the Associative array Wikipedia article
u
user278064
var global = (function() {
   return this;
})();

// Pair object, similar to Python

function Pair(key, value) {
    this.key = key;
    this.value = value;

    this.toString = function() {
       return "(" + key + ", " + value + ")";
    };
}

/**
 * as function
 * @param {String} dataName A String holding the name of your pairs list.
 * @return {Array:Pair} The data list filled
 *    with all pair objects.
 */
Object.prototype.as = function(dataName) {
    var value, key, data;
    global[dataName] = data = [];

    for (key in this) {
       if (this.hasOwnProperty(key)) {
          value = this[key];

          (function() {
             var k = key,
                 v = value;

            data.push(new Pair(k, v));
          })();
       }
    }

    return data;
};

var d = {
   'one': 1,
   'two': 2
};

// Loop on your (key, list) pairs in this way
for (var i = 0, max = d.as("data").length; i < max; i += 1) {
   key = data[i].key;
   value = data[i].value;

   console.log("key: " + key + ", value: " + value);
}

// delete data when u've finished with it.
delete data;