先给出数组
var array = ["囚徒","过客","领袖"];//职场3种人
var o = {0:"linda",1:"style",2:"nick",length:3};
一、 do while
(function() {
var i = 0,
len = array.length;
do {
if (i == 2) {
break; // 循环被终止, 此处如果是continue就会造成循环无法退出
};
console.log('array['+ i +']:' + array[i]);
i++;//此句建议放置循环while头部
} while(i<len);
})();
do/while的语法简化了循环的实现, 只保留对循环条件的判断, 所以我们要在循环内部构造出循环退出的条件, 否则有可能造成死循环. 特别要注意的是: 使用 continue 跳出本次遍历时, 要保证循环能够自动进入到下一次遍历, 因此保证循环走到下一次遍历的语句需要放到 continue 前面执行, 建议置于循环头部.(如上, i++ 语句最好放置循环头部)
do/while 循环与for循环大体差不多,只支持数组遍历, 多用于对循环退出条件不是很明确的场景. 一般来说不建议使用这种方式遍历数组.
二、labeled 语句
一个 label 提供了一个可以让你引用到您程序别的位置的标识符。例如,你可以用 label 标识一个循环, 然后使用 break 或者 continue 来指出程序是否该停止循环还是继续循环。
var x = 0;
var z = 0
labelCancelLoops: while (true) {
console.log("外部循环: " + x);
x += 1;
z = 1;
while (true) {
console.log("内部循环: " + z);
z += 1;
if (z === 10 && x === 10) {
break labelCancelLoops;
} else if (z === 10) {
break;
}
}
}
三、break 语句/continue语句(不做过多解释)
break 语句用于跳出循环。
continue 用于跳过循环中的一个迭代。
四、for
语法: for(初始化; 循环执行条件; 每遍历一个元素后做的事情;){}
(function(){//循环置于闭包之内
for(var i=0,length=array.length;i<length;i++){//缓存数组长度
console.log(array[i]);//内部方法若有可能相互影响,也要置于闭包之内
}
})();
for循环只能遍历数组, 不能遍历对象. 写for循环时有两点需要注意.
1、 为了避免遍历时执行多遍计算数组长度的操作, 影响效率, 建议在循环开始以变量的形式缓存下数组长度, 若在循环内部有可能改变数组长度, 请务必慎重处理, 避免数组越界.
2、JavaScript中并没有类似java的块级作用域, for循环内部定义的变量会直接暴露在外(如 i,循环退出后,i变量将等于数组长度, 后续代码将能访问到 i 变量的值), 因此建议将for循环置于闭包内. 特别要注意的是: 如果在循环内部, 前一个元素的遍历有可能影响到后一个元素的遍历, 那么for循环内部方法也需要置于闭包之内.
五、forEach
语法: array.forEach(function(item){}), 参数item表示数组每一项的元素;
array.forEach(function(item, index, array), thisValue)多参数
array.forEach(function(item){
if(item=="囚徒")
return;//这里只能使用return跳过当前元素处理
console.log(item);
});
forEach回调function默认有三个参数: item, index, array.
使用forEach循环有几点需要特别注意:
1、forEach无法遍历对象
2、forEach无法在IE中使用,只是在firefox和chrome中实现了该方法
3、forEach无法使用break,continue跳出循环,使用return时,效果和在for循环中使用continue一致
六、for...in...
语法: for(var item in array){}
遍历对象的可枚举属性,以及对象从其构造函数原型中继承的属性,一般不建议使用for…in遍历数组,因为顺序是不确定的,取决于宿主环境。
for(var item in array){
console.log(item);
}//0 1 2
for(var item in o){
console.log(item);
}//0 1 2 length
for in 可用于遍历数组和对象, 但它输出的只是数组的索引和对象的key, 我们可以通过索引和key取到对应的值. 如下:
for(var item in array){
console.log(array[item]);
}//"囚徒" "过客" "领袖"
for(var item in o){
console.log(o[item]);
}//"linda" "style" "nick" "length"
for...in 遍历数组的缺点:
数组的键名是数字,但是for…in循环是以字符串作为键名“0”、“1”、“2”等等。
for…in循环不仅遍历数字键名,还会遍历手动添加的其他键,甚至包括原型链上的键。
某些情况下,for…in循环会以任意顺序遍历键名。
七、for...of...
es6 新推出的 for...of 循环方式,性能和 for 循环差不多,推荐使用 for...of 遍历数组和对象
for...of 遍历对象:
let obj = {name: 'jeff', age: 20, sex: 'male'}
// 对于普通的对象,for...in循环可以遍历键名,for...of循环会报错(因为没有部署 Iterator 接口)。
// 一种解决方法是,使用Object.keys方法将对象的键名生成一个数组,然后遍历这个数组。
for (let key of Object.keys(obj)) {
console.log(key + ' : ' + obj[key])
}
for...of 遍历数组:
let arr = [1, 2, 3]
for (let item of arr) {
console.log(item)
}
八、map即 Array.prototype.map,该方法只支持数组
语法: array.map(callback[,thisArg]) map方法使用其提供函数的每次返回结果生成一个新的数组.
var array = [1, 4, 9];
var roots = array.map(Math.sqrt);//map包裹方法名
// roots is now [1, 2, 3], array is still [1, 4, 9]
var array = [1, 4, 9];
var doubles = array.map(function(num) {//map包裹方法实体
return num * 2;
});
// doubles is now [2, 8, 18]. array is still [1, 4, 9]
实际上,由于map方法被设计成支持 [鸭式辨型][] , 该方法也可以用来处理形似数组的对象, 例如 NodeList.
var elems = document.querySelectorAll('select option:checked');
var values = Array.prototype.map.call(elems, function(obj) {
return obj.value;
});
甚至还可以用来处理字符串, 如下:
var map = Array.prototype.map;
var array = map.call('Hello 中国', function(x) {
return x.charCodeAt(0);
});
console.log(array);
//[72, 101, 108, 108, 111, 32, 20013, 22269]
map处理字符串的方式多种多样, 例如 反转等.
var str = '12345';
var output = Array.prototype.map.call(str, function(x) {
return x;
}).reverse().join('');
console.log(output);//54321
例如 将字符串数组转换为数字数组, 只需一条语句, 如下:
console.log(['1', '2', '3'].map(Number));//[1,2,3]
目前map方法被大部分浏览器支持, 除了IE 6,7,8.
九、every即 Array.prototype.every, 该方法同上述map方法也只支持数组
语法: arr.every(callback[, thisArg]) every 方法用于检验数组中的每一项是否符合某个条件, 若符合则放回true, 反之则返回false.
function isBigEnough(element, index, array) {
return element >= 10;
}
[12, 5, 8, 130, 44].every(isBigEnough); // false
[12, 54, 18, 130, 44].every(isBigEnough); // true
该方法还有简写方式, 如下:
[12, 5, 8, 130, 44].every(elem => elem >= 10); // false
[12, 54, 18, 130, 44].every(elem => elem >= 10); // true