我是JavaScript新手,目前我正在学习所谓的for... in
循环。适用于JavaScript循环吗?
在JavaScript中编码时,实际上是否使用这些循环?
我可以看到所有其他类型的循环是如何有用 - 但不是这一个。
有人对此有所了解,请尽可能包含真实生活中的示例。
我是JavaScript新手,目前我正在学习所谓的for... in
循环。适用于JavaScript循环吗?
在JavaScript中编码时,实际上是否使用这些循环?
我可以看到所有其他类型的循环是如何有用 - 但不是这一个。
有人对此有所了解,请尽可能包含真实生活中的示例。
仅在Javascript中可以使用正常的for(;;)
循环迭代Array对象。该for..in
用于非数组对象的枚举:
for (var i in obj) {
if (obj.hasOwnProperty(i)) { // if you don't want to access prototype properties
alert(i);
alert(obj[i]);
}
}
它通常用于遍历的东西集合。例如,因为每个JavaScript对象都可以看作属性的集合,所以可以按照这种方式枚举属性。
//let's loop throug all properties of a "document"
//we don't know what these will be
var txtProps = "";
for (var prop in window.document) {
txtProps += prop + "\n";
}
alert(txtProps);//pops out a message showing a looong list of all properties
我认为没关系,只要你明白一个对象可以容纳的不仅仅是简单的变量。考虑下面这个例子,从w3schools.com修改,以说明这一点:
<script type="text/javascript">
//This is probably as you expect:
var person={fname:"John",lname:"Doe",age:25};
//This is probably unexpected and unwanted, but is valid and will be an output of the for...in loop:
person.f = function(){
alert("Hi");
};
//Use typeof() function to check that the data type is what you expect:
for (x in person){
document.write(typeof(person[x]) + " ");
}
</script>
此打印:
串串数字功能
要获得关于环路类型,则对之间的差异具体问题()循环适用于具有length属性的数组类型。 foreach()循环可以很好地用于迭代对象集合,而foreach ... in循环对于对象的键(对于任何类型的循环都不会声称这些是唯一用途)很适用。
为了理解这一点,您首先需要了解JavaScript的对象模型。
正如你所指出的,当使用数组时,for...in
循环并不是那么有用,因为for (;;)
循环更容易完成这项工作。
但是数组只是一种具有数字属性的JavaScript对象,并且for (;;)
循环仅处理数字属性。符号myArray[0]
的原因是,您可以对任何属性名称使用此方括号表示法。因此myObject['myProperty']
与myObject.myProperty
相同。这是for...in
变成有用:
for (var i in myObject) {
alert(myObject[i]);
}
因此,如果我们想设置的唯一属性是myProperty
,然后i
将等于"myProperty"
(注意,这是一个字符串,这使得它不仅仅是作为一个变量名更动态) 。
虽然这里有一个巨大的但是。对象有一些叫做原型的东西,这些原型有自己的属性和方法。如果我做到以下几点:
for (var i in myArray) {
alert(i + ': ' + myArray[i]);
}
...我不会一下就惊动用数值(1,2,3等),我也会得到警告与阵列的属性,如length
,及其方法如join
。这些特性实际上属于Array对象的原型,原型属性可以通过做被过滤了以下工作:
for (var i in myArray) {
if (myArray.hasOwnProperty(i)) {
alert(i + ': ' + myArray[i]);
}
}
现在我就把与数值再次提醒,这意味着这是(几乎)完全相同与for (var i = 0;; i < myArray.length; i++)
相同。为什么当我们能够使用这种符号时,我告诉你这一点?因为所有的对象都有原型,而不仅仅是数组。并且每个对象都从Object
对象开始下降,因此如果有人定义了Object.prototype.myProperty = "some string value"
,那么该对象总会出现在您在页面的其余部分使用的任何for...in
循环中。谢天谢地,hasOwnProperty
方法本身属于Object.prototype
,所以你可以(也应该)总是在你的for...in
循环中使用它。
因此,这里是一个完全成熟的for...in
例如:
// This is just one way of defining an object. We could also use a constructor function, or `new Object()`
var myObject = {
aProperty : "my first property value",
anotherProperty : "second property value"
4 : "numeric property names work too, you know"
}
for (var i in myObject) {
if (myObject.hasOwnProperty(i)) {
document.write(i + ': ' + myObject[i] + '<br />\n');
}
}
输出:
aProperty: my first property value
anotherProperty: secondPropertyValue
4: numeric property names work too, you know
希望这可以解释这一切。
for in
和for
都用于特定目的。让我们看看一些。
如果你有一个对象
var obj = { one: 1, two: 2 };
然后你可以遍历它的使用for in
循环特性即
for(var i in obj) console.log(obj[i]); //use obj.hasOwnProperty(i) to exclude prototype properties
的注意,如果你试图通过迭代obj
for循环它将不会工作,因为它会使用数字索引来访问密钥,并会给一个未定义的,即obj[0]
将是未定义的。这不在于形成一个事实,即获得一个对象的长度会比简单地编写obj.length
更为复杂。当然,如果你有数字属性,你可以使用for
循环,for in
更适合用于对象迭代。
如果你有一个阵列
var array = [1,2]
你可以在技术上使用这两种但我们建议您使用for循环这一点。这是为什么
为了说明第二点,让我们扩展Array。
Array.prototype.print_array = function(){ console.log(this) };
,我们只是添加到阵列该功能将所有的数组对象继承,因此,通过for in
for(var i in array) console.log(array[i]);
迭代阵列上会产生
1
2
function(){ console.log(this) } // the prototype property was iterated over also
并遍历在阵列上与for
for(var i =0; i < array.length; i++) console.log(array[i]);
会产生预期的结果。
1
2
因此,对于对象重复使用for in
和数组迭代使用for
同意约hasOwnProperty(),但你也可能要检查的typeof(),以确保功能类型等别你最终会输出。 –
@MickSear完全取决于你对对象做什么。例如,如果你使用遍历来“克隆”对象,那么你并不在乎。无论如何,我只是添加了它,因为这是他可能遇到的问题,与问题本身并没有真正的关系。 – deviousdodo
就像一个笔记:我的答案只是关于一般的做法,我忽略了一些技巧。 'arguments'是'只有数组对象可以被迭代'的一个例外,当然''for'循环只是偶尔用于遍历数组,但我认为这些事情对于这个问题本身并不重要。 – deviousdodo