【小家java】java5新特性(简述十大新特性) 重要一跃
【小家java】java6新特性(简述十大新特性) 鸡肋升级
【小家java】java7新特性(简述八大新特性) 不温不火
【小家java】java8新特性(简述十大新特性) 饱受赞誉
【小家java】java9新特性(简述十大新特性) 褒贬不一
【小家java】java10新特性(简述十大新特性) 小步迭代
【小家java】java11新特性(简述八大新特性) 首个重磅LTS版本
java一共提供了3中循环语法:for循环(含增强for循环)、while循环、do…while循环。java8之后提供了基于stream的foreach循环,然后本文就针对于这几个循环,分别介绍一下循环控制语句:break,continue,return对循环体的影响。
特别隆重介绍:foreach循环中,如何停止本次循环和停止所有循环,因为stream的使用非常方便和广泛
最先开始,直接上主菜for循环,后面再介绍稍微简单的例子while循环等。
先来看一个最简单的循环体:
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
System.out.print(i + ",");
}
}
输出:
0,1,2,3,4,5,6,7,8,9,
接下来,我们加入一些循环控制语句,看看效果:
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
if (i < 5) {
continue;
}
System.out.print(i + ",");
}
}
输出:
5,6,7,8,9,
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
System.out.print(i + ",");
if (i < 5) {
break;
}
}
}
输出:
0,
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
System.out.print(i + ",");
if (i < 5) {
return;
//return false; //编译报错
//return true; //编译报错
}
}
}
输出:
0,
从结果中很容易看出,for循环里的continue是结束本次循环继续下一次循环,break是结束当前for所有循环。而return表面上看效果和break一样,确实如此。但是,但是,但是需要注意:return其实是退出方法,它退出的层次是很高的,如果方法体只有一个for循环,效果一样。因此不同的场景,有时候用break,有时候用return,需要注意。
若只想退出for循环,并不想退出方法体,用break;
若退出for循环并且退出方法体,用return;
接下来简单说一下增强for循环(JDK5以后的新特性):
public static void main(String[] args) {
List<String> lists = new ArrayList<>();
lists.add("a");
lists.add("b");
for (String str : lists) {
System.out.print(str + ",");
}
}
输出:
a,b,
这里不介绍增强for的循环控制,我简要解释一下增强for其实只是个语法糖,大家就理解了。把我编译之后的.class文件的增前for贴出来,大家应该就不需要继续介绍了:
上面增强for编译过后代码如下:
public static void main(String[] args) {
List lists = new ArrayList();
lists.add("a");
lists.add("b");
Iterator var2 = lists.iterator();
while(var2.hasNext()) {
String str = (String)var2.next();
System.out.print(str + ",");
}
}
我们发现增强for循环遍历和iterator遍历反编译后的字节码完全一样,所以增强for不用解释了,直接参考for循环和while循环的一些特点就行了
接下来,最重要的主菜登场:foreach循环。
随着java8的普及,基于流式的编程日益普及。它能使得代码的结构越发清晰并且效率也是大大的提升啊,因此我们平时在使用foreach循环的频率就越高了。但是大家或多或少都遇见类似头疼的问题:发现continue和break甚至return语法对foreach循环都不好使了
下面看看示例代码:
public static void main(String[] args) {
List<Integer> lists = Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
lists.forEach(x -> {
if (x < 5) {
//continue; //编译报错
//break; //编译报错
//return false; //编译报错
return;
}
System.out.print(x + ",");
});
}
输出:
5,6,7,8,9,10,
通过上述结果,我们可以得出如下结论:
因此,foreach虽然好用效率高,但也有它的局限性,各位可以根据自己的需求选择遍历方式。
例如下面代码:getDate被调用...
会被打印输出多少次呢?
public static void main(String[] args) {
System.out.println("================普通for循环:");
for (int i = 0; i < getData().size(); i++) {
System.out.println(i);
}
System.out.println("================增强for循环:");
for (Integer i : getData()) {
System.out.println(i);
}
System.out.println("================Java8提供的foreach循环:");
getData().forEach(System.out::println);
}
private static List<Integer> getData() {
System.out.println("getDate被调用...");
var list = new ArrayList<Integer>();
list.add(10);
list.add(20);
list.add(30);
return list;
}
结果:
输出3次
输出1次
输出1次
有了这个结果,咱们以后使用for循环的时候,不需要定义的变量,就可以节省下来了,也显得我们对for循环原理更加的理解深入,高大上(装逼)的体现
其实原因很简单:我贴上.class文件的源码,一目了然,就不再解释了:
public static void main(String[] args) {
System.out.println("================普通for循环:");
for(int i = 0; i < getData().size(); ++i) {
System.out.println(i);
}
System.out.println("================增强for循环:");
Iterator var3 = getData().iterator();
while(var3.hasNext()) {
Integer i = (Integer)var3.next();
System.out.println(i);
}
System.out.println("================Java8提供的foreach循环:");
List var10000 = getData();
PrintStream var10001 = System.out;
System.out.getClass();
var10000.forEach(var10001::println);
}
关于while循环和do…while循环的控制,和for循环的一模一样,因此这里不再做讨论了,各位可以自己在本机尝试一下。
最后再聊聊循环嵌套。最常见的就是for循环里面还有for循环,甚至3层或者更多层的循环嵌套。咱们先不讨论现实中允不允许这么去写代码,但从语法角度java是支持的,毕竟有些极其特殊的需求,还真得这么做。
关于循环嵌套,有时候我们希望通过continue、break等语句精准的控制具体的哪一层循环,从而达到我们的目的。java为了满足这种需求,支持了给循环**起别名(打标签)**的方式(for循环和while循环都可以其别名),基本语法也很简单,可看下面例子,打印9*9乘法表:
public static void main(String[] args) {
a: for (int i = 1; i <= 9; i++) {
b: for (int j = 1; j <= 9; j++) {
System.out.print(j + "*" + i + "=" + (j * i) + "\t");
if(j >= i){
System.out.println();
continue a; //直接继续外层循环
}
}
}
}
输出:
1*1=1
1*2=2 2*2=4
1*3=3 2*3=6 3*3=9
1*4=4 2*4=8 3*4=12 4*4=16
1*5=5 2*5=10 3*5=15 4*5=20 5*5=25
1*6=6 2*6=12 3*6=18 4*6=24 5*6=30 6*6=36
1*7=7 2*7=14 3*7=21 4*7=28 5*7=35 6*7=42 7*7=49
1*8=8 2*8=16 3*8=24 4*8=32 5*8=40 6*8=48 7*8=56 8*8=64
1*9=9 2*9=18 3*9=27 4*9=36 5*9=45 6*9=54 7*9=63 8*9=72 9*9=81
若不用for循环别名,需要这么些:
public static void main(String[] args) {
for (int i = 1; i <= 9; i++) {
for (int j = 1; j <= i; j++) {
System.out.print(j + "*" + i + "=" + (i * j) + "\t");
}
System.out.println();
}
}
输出:同上
这种写法,可能for (int j = 1; j <= i; j++)这句话稍微有那么点难理解点。两种方式各有优劣,各位可以根据具体情况具体选择
循环的使用场景无处不在,传统每一份逻辑代码。然后此文重点解惑了:foreach循环中的逻辑控制语句怎么使用的问题。希望掌握这个知识点后,遍历尽量的可以使用更加高效的foreach来控制代码结构,当然stream流式编程也是被推荐的。
我的微信公众号也会持续推送技术干货,欢迎下方二维码扫码关注获取。
更多内容持续更新中,欢迎关注我的博客!
有任何问题,可以跟我留言讨论,欢迎指正,不胜感激。
有任何疑问,亦可扫码向我提我哟~