在英文中,Loop
這個字指的是由彎曲的曲線所產生的形狀。類似的概念,Loop
這個字已經被用來做程式設計。如果你看到下圖,你就會清楚的知道指令的流動是如何在一個循環的動作中不斷重複的。在程式設計中,循環的概念並不是什麼新概念,它們常常在編碼時使用。雖然不是的語言其語法不同,但基本概念是相同的,根據需要重複相同的程式碼區塊。 JavaScript增加了循環類型(包括各種類型的循環),並使其與它們的工作更加舒適和高效。在本文中,我們將學習JavaScript中所有可用的循環。
在電腦程式設計中,Loop
是一個重複特定程式碼區塊的過程。
在JavaScript中有七種迴圈型別。我們已經把它們列出來,這可以幫助你更清楚地了解他們的工作流程和使用情況。本文也將幫助你區分這七種循環類型,例如在哪裡、何時或如何使用它們。讓我們開始吧。
while
循環while
循環是JavaScript中可用的最基本的循環類型之一。你一定聽過,JavaScript不是唯一的程式語言。
while
語句產生一個循環,在條件為true
的情況下,在一個特定的語句區塊中執行該迴圈。每次執行程式碼區塊之前,條件都會被檢查。
while (条件) { // 代码块}
var i = 8;while (i < 10) { console.log('我小于10') i++ }
在上面的範例中,條件(i < 10)
先會被檢查,如果條件為true
,while
中的程式碼區塊就會被執行,而且再下一次迭代之前,i
的值將增加1
#,主要是因為我們已經加入了一個i++
語句。
do-while
循環do-while
和while
略有不同,因為它包含一個額外的特性,最少執行一次。
do { // 代码块}while (条件)
var i = 8;do { console.log('我的值是' + i) i++ }while (i > 7 && i < 10)
你可以看到,我們的條件是(i > 7 && i < 10)
,但i=7
的時候值已經印出來了。因為這個循環技術先執行程式碼區塊,而不是考慮條件,執行完程式碼區塊之後,在第二輪的時候才執行條件。對於第二次循環遍歷程式碼區塊時,只有條件為true
才會執行。
for
迴圈while
迴圈和for
迴圈的工作方式完全相同,即使執行時間也沒有太大差別。那麼,另一個提供相同功能的循環系統需要什麼呢?
在for
迴圈中,迴圈的變數宣告和初始化,條件查詢和迴圈變數的遞增或遞減都可以在相同的行中完成。它增加了可讀性,並降低了出錯的幾率。
for ([变量初始化];[条件];[变量递增或递减]) { // 代码块 }
for (var i = 0; i < 10; i++) { console.log('我的值是: ' + i) }
如上面的範例所示,變數初始化i = 0
,條件i < 10
和變數的遞增i++
都在同一行宣告。它更容易理解,可讀性更好,是不是?
for
迴圈的使用和前面所說的while
迴圈完全相同。但是為了讓程式碼更容易閱讀和理解,大多數的時候我們使用for
循環而不是while
循環。
forEach()
它是陣列的原型方法(甚至是map
和set
)。 forEach()
方法根據索引順序index
,每次使用陣列中的每個元素呼叫一個給定的函數(或回調函數)。請注意,forEach()
沒有對沒有值的陣列元素執行給定的函數。
array.forEach(function(currentValue, index, array){ // 函数主体})
forEach()
方法以函數作為參數。此函數由三個參數組成:
currentValue
:保存正在處理的目前值
index
:儲存該特定陣列中的值的索引
array
:儲存了整個陣列
你可以使用forEach()
來遍歷一個集合set
,也可以用它來迭代一個映射map
。
var array = [10, 20, "hi", , {}, function () {console.log('我是一个函数')}]array.forEach(function(item, index){ console.log('array [' + index + '] 是: '+ item) })
forEach()
方法遍歷的是array
陣列。如果你沒有使用索引index
,你只能使用array.forEach(function(item){})
。可以相應地使用參數,但不是每次都要使用這三個參數。
使用forEach()
讓我們遍歷陣列變得非常的簡單。不必擔心循環變數、條件和其他任何東西,它會處理所有迭代的問題。
forEach()
和for
的区别你可以使用一个从0
开始到array.length
(该数组长度)简单的遍历一个数组。那么为什么还要提出不同的选择呢?
一个经验法则是,如果你可以选择使用原型方法,你就应该使用原型方法。因为,原型方法更清楚地知道对象,并对最佳方法进行了优化。下面这个示例能更好的来说明他们的区别之处:
var arr = []; arr[0]=0; arr[10]=10;for(var i=0; i<arr.length; i++){ console.log("I am for:" + i); } arr.forEach(function(){ console.log("I am forEach"); });
如果你运行上面的代码,你会发现for
打印了11
次,而forEach()
只打印了两次:
原因是,for
循环是一个简单的for
循环,对它的用途一无所知。它从0
到arr.length
。然而,当你使用forEach()
的时候,它知道arr
只有两个元素,虽然长度是10
。累此,它实际上只迭代了两次。
根据这个,如果你想在循环中跳过繁重的工作,迭代一个iterable
,你应该使用forEach()
。然而,仅仅迭代(相同数量的迭代)的迭代时间相对于for
循环来说是次要的。因为迭代性能更好。
map()
map
是数组的另一个原型方法。map()
方法将创建一个新的数组,该数组的返回值由一个给定的数组的函数执行生成。
var newArray= oldArray.map(function (currentValue, index, array){ //Return element for the newArray});
map()
方法以函数作为参数,该函数有三个参数:
currentValue
: 在数组中处理的当前元素
index
:数组中正在处理的当前元素的索引值
array
:数组映射的调用
var num = [1, 5, 10, 15];var doubles = num.map(function(x) { return x * 2; });
在上面的示例中,名为doubles
的新数组将输出doubles=[2, 10, 20, 30]
和num
数组仍旧是num=[1, 5, 10, 15]
。
这个方法主要是对象的迭代。for...in
在语句中迭代对象的可枚举属性。对于每个不同的属性,可以执行语句。
因为我们知道数组也是一种特殊的对象,所以不要认为数组不能用这个来进行迭代。
for (variableName in object) { Block of code }
var obj = {a: 1, b: 2, c: 3}; for (var prop in obj) { console.log('obj.'+prop+'='+obj[prop]); };
为什么在数组中使用for...in
迭代不可取?
for...in
不应该在数组迭代中使用,特别是index
顺序非常重要。
实际上,数组索引和一般对象属性之间没有区别,数组索引只是可枚举属性。
for...in
不会每次都以任何特定的顺序返回index
值。for...in
在迭代中,这个循环将返回所有可枚举属性,包括那些具有非整数名称的属性和继承的属性。
因此,建议在遍历数组时使用for
或forEach()
。因为迭代的顺序是依赖于现实的迭代,并且遍历一个数组,使用for...in
可能不会以一致的顺序访问元素。
var arr = []; arr[2] = 2; arr[3] = 3; arr[0] = 0; arr[1] = 1;
在这种情况下,使用forEach()
将输出一个0, 1, 2, 3
。但使用for...in
并不能保证会输出什么。
对于for...in
还有一件事你应该记住,它遍历对象的所有属性,包括继承的(来自父类)。如果只想在对象自己的属性上进行迭代,那么应该执行下面这样的操作:
for(var prop in obj){ if(obj.hasOwnProperty(prop)){ Code block here } }
这是ES6中新引入的一种循环类型。使用for...of
语句,你可以遍历任何可迭代的对象,比如Array
、String
、Map
、WeakMap
、Set
、参数对象、TypeArray
,甚至一般对象。
for (variable of iterable) { Block of code }
var str= 'paul';for (var value of str) { console.log(value); }
let itobj = new Map([['x', 0], ['y', 1], ['z', 2]]);for (let kv of itobj) { console.log(kv); }// => ['x', 0]// => ['y', 1]// => ['z', 2]for (let [key, value] of itobj) { console.log(value); }// => 0// => 1// => 2
for...in
循环主要遍历对象,其实际的插入顺序中是可枚举的属性;for...of
迭代任何可迭代对象的给定值(而不是属性名)。
Object.prototype.objProto = function() {}; Array.prototype.arrProto = function() {};let iterable = [8, 55, 9]; iterable.title = 'VoidCanvas';for (let x in iterable) { console.log(x); // logs 0, 1, 2, title, arrProto, objProto}for (let i of iterable) { console.log(i); // 8, 55, 9}
正如你所见,for...of
都是关于对象自己value
的迭代,而for...in
将会考虑原型和继承的属性。如果你想在对象上迭代(而不是迭代)。for...of
将会考虑它自己的所有属性,但迭代的情交下,它只会考虑适合这种迭代的元素。这就是为什么在上面的例子中,for...of
没有迭代属性。
相关推荐:
以上是JavaScript中循環類型總結分析的詳細內容。更多資訊請關注PHP中文網其他相關文章!