Java真的不难(二十五)Stream流

Java真的不难(二十五)Stream流小应学长带你学 Java

Stream流

上篇文章讲了Java 8 的一个新特性:Lambda表达式,在业务中若能熟练的使用,可以节省很多代码量,看着也整洁很多。那么这篇文章将介绍另一个新特性:Stream流,不要看错哈!!!不是打游戏的steam!!

1、什么是Stream流:

Stream 是Java 8 提出的一个新概念,不是输入输出的 Stream 流 (和IO流其实没有任何关系哈),而是一种使用函数式编程方式在集合类上进行操作的工具。简而言之,是以内部迭代的方式处理集合数据的操作,内部迭代可以将更多的控制权交给集合类。Stream 和 Iterator 的功能类似,只是Iterator 是以外部迭代的形式处理集合数据的操作。

当然Stream也有自己特性:

  1. 不是一种数据结构,不会存数据,只是在原数据集上定义了一组操作
  2. 这些操作是惰性的,即每当访问到流中的一个元素,才会在此元素上执行这一系列操作
  3. 因为不保存数据,故每个Stream流只能使用一次。

Stream流的实现图:
在这里插入图片描述

2、创建流:

想要用Stream流来操作集合,那么就需要将数组或者集合先转换成Stream流才可以操作

Stream的官方文档:

https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/util/stream/Stream.html

先来看四个方法:

  1. filter:通过lambda表达式来实现条件过滤
  2. limit:截取流,截取一段流
  3. skip:跳过流
  4. distinct:去除重复

创建Stream:

public class Test { 
    public static void main(String[] args) { 
    String [] arr = { 
   "东","南","西","北"}; //将数组转换成Stream Stream<String> stream = Arrays.stream(arr); stream = Stream.of(arr); stream = Stream.of("东","南","西","北"); //将list集合转换成stream List<String> list = Arrays.asList("aa","cc","bb","aa","dd"); stream = list.stream(); //排序、去重、遍历 list.stream().sorted().distinct().forEach(System.out::println); //用过Stream流操作完集合后还可以再转换成一个新的集合 List<String> newList = list.stream().sorted().distinct().collect(Collectors.toList()); System.out.println(newList.toString()); } } 

输出:

//遍历并去重后的结果: aa bb cc dd //用过Stream流操作完集合后还可以再转换成一个新的集合 [aa, bb, cc, dd] 

四个方法的操作:
Person类:

这个类代码比较多,所有不把get/set方法写进去了,大家的使用的时候别忘!!

public class Person { 
    private String name; private Integer age; private String country; private char sex; @Override public String toString() { 
    return "信息表:{" + "name='" + name + '\'' + ", age=" + age + ", country='" + country + '\'' + ", sex=" + sex + '}'; } //这里节省的get/set代码 //重写toString() 和 equals 和 hashcode 方法 @Override public boolean equals(Object o){ 
    if(this == o) return true; if(o == null || getClass() != o.getClass()) return false; Person person = (Person) o; if(country != null){ 
    if(this.country.equals(person.country)){ 
    return true; }else{ 
    return false; } } return false; } @Override public int hashCode(){ 
    return Objects.hash(country); } } 

测试类:

结合了lambda表达式来写

public class Test { 
    public static void main(String[] args) { 
    List<Person> perosnList = new ArrayList<>(); perosnList.add(new Person("王一", 30, "中国", 'M')); perosnList.add(new Person("张三", 19, "美国", 'F')); perosnList.add(new Person("李四", 29, "日本", 'F')); perosnList.add(new Person("小美", 74, "英国", 'M')); perosnList.add(new Person("熊二", 15, "意大利", 'F')); perosnList.add(new Person("熊大", 66, "韩国", 'F')); //返回年龄大于20岁的学生集合 System.out.println("返回年龄大于20岁的学生集合"); perosnList.stream().filter(p -> p.getAge() > 20).forEach(System.out::println); //返回年龄大于50岁的学生集合 System.out.println("返回年龄大于50岁的集合"); List<Person> list = perosnList.stream().filter(p -> p.getAge() > 50).collect(Collectors.toList()); System.out.println(list); //返回年龄大于20岁的中国学生 System.out.println("返回年龄大于20岁的中国人"); perosnList.stream().filter(p -> p.getAge() > 20).filter(p -> p.getCountry().equals("韩国")).forEach(System.out::println); //年龄大于20 中国 性别M System.out.println("返回年龄大于20 中国 性别M"); perosnList.stream().filter(p -> p.getAge() > 20 && p.getCountry().equals("中国") && p.getSex() == 'M').forEach(System.out::println); } } 

看看结果:

返回年龄大于20岁的学生集合 信息表:{ 
   name='王一', age=30, country='中国', sex=M} 信息表:{ 
   name='李四', age=29, country='日本', sex=F} 信息表:{ 
   name='小美', age=74, country='英国', sex=M} 信息表:{ 
   name='熊大', age=66, country='韩国', sex=F} 返回年龄大于50岁的集合 [信息表:{ 
   name='小美', age=74, country='英国', sex=M}, 信息表:{ 
   name='熊大', age=66, country='韩国', sex=F}] 返回年龄大于20岁的中国人 信息表:{ 
   name='熊大', age=66, country='韩国', sex=F} 返回年龄大于20 中国 性别M 信息表:{ 
   name='王一', age=30, country='中国', sex=M} 

小结:
使用Stream流可以容易操作数组或者集合,可以结合Lambda表达式,可以让一句表达式整洁明了,其实既然是Java退出的新特性,那么肯定是有用处的。

3、Stream的map映射流

public class Test { 
    public static void main(String[] args) { 
    //map的作用是迭代取到每个list元素,再通过map里面的函数进行相应的操作 List<String> list1 = Arrays.asList("a","bb","ccc","dddd"); //通过map取到每个集合元素的长度并返回 Stream<Integer> stream = list1.stream().map(p->p.length()); stream.forEach(System.out::println); System.out.println("----------------"); List<String> userList = new ArrayList<>(); userList.add("周杰伦.tom"); userList.add("尼古拉斯.赵四"); userList.add("牛顿.巴基斯"); userList.add("赵少华.思密达"); List<String> uList = userList.stream().map(p->p.substring(p.indexOf(".")+1, p.length())).collect(Collectors.toList()); System.out.println(uList.toString()); } } 

输出:

1 2 3 4 ---------------- [tom, 赵四, 巴基斯, 思密达] 

4、Stream查找与匹配

Stream内还有一个 anyMatch(Predicate
predicate)
的方法:
返回此流中的任何元素是否匹配所提供的词

Demo:

public class Test { 
    public static void main(String[] args) { 
    List<String> list = Arrays.asList("周杰伦","王力宏","孙燕姿","林俊杰"); boolean flag1 = list.stream().anyMatch(ele->ele.contains("燕")); System.out.println("有没有名字包含燕的同学:"+flag1); //判断开头: boolean flag2 = list.stream().anyMatch(ele->ele.startsWith("王")); System.out.println("有没有名字开头是王的同学:"+flag2); //判断结尾: boolean flag3 = list.stream().anyMatch(ele->ele.endsWith("杰")); System.out.println("有没有名字结尾是杰的同学:"+flag3); // anyMatch是匹配所有的,要满足条件 boolean flag4 = list.stream().anyMatch(ele->ele.length()>2); System.out.println("所有同学的名字都是两个字以上的吗"+flag4); boolean flag5 = list.stream().anyMatch(ele->ele.startsWith("王")); System.out.println("所有同学的名字都有王吗?"+flag5); //noneMatch boolean flag6 = list.stream().noneMatch(ele->ele.contains("燕")); System.out.println("集合中都没有包含'燕'这个字吗"+flag5); } } 

输出:

有没有名字包含燕的同学:true 有没有名字开头是王的同学:true 有没有名字结尾是杰的同学:true 所有同学的名字都是两个字以上的吗true 所有同学的名字都有王吗?true 集合中都没有包含'燕'这个字吗true 

使用anyMatch()里面的方法可以很容易对这个流的信息匹配。

在这里插入图片描述

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/216575.html原文链接:https://javaforall.net

(0)
上一篇 2026年3月18日 上午11:33
下一篇 2026年3月18日 上午11:33


相关推荐

  • FabricJS gotchas/FabricJS陷阱[通俗易懂]

    FabricJS gotchas/FabricJS陷阱[通俗易懂]FabricJSgotchas这个页面包含了第一次接触fabricJS的人打开的最常见问题的列表。这些缺陷的产生,既有解释不清的原因,也有文档不完善的原因。在这里,我们试图解决共同的问题。Objectsarenomoreselectable-setCoords(对象不再是可选择的-setCoords)Fabric包含两组坐标以快速知道物体在画布上的位置。它们链接到两个对象属性:oCoords和aCoords。当用户与对象交互或结束变换(例如拖动)时,fabricJS会自动更新这些坐标。

    2025年8月5日
    4
  • BM3D的学习与Matlab实现「建议收藏」

    BM3D的学习与Matlab实现「建议收藏」                    BM3D的学习与Matlab的实现      BM3D是2007年TIP的文章,题目是《ImageDenoisingbySparse3-DTransform-DomainCollaborativeFiltering》。最近想尝试一下图像去噪,看看能否应用到项目中,顺便测试了一下效果,结果不…

    2022年5月2日
    36
  • 本地安装部署openclaw(最新版)

    本地安装部署openclaw(最新版)

    2026年3月13日
    2
  • fastRcNN算法路面病害检测_R语言经典算法

    fastRcNN算法路面病害检测_R语言经典算法  FastR-CNN算法是作者RossGirshick继R-CNN后的又一力作。R-CNN虽然取得了不错的成绩,但是其缺点也很明显。FastR-CNN同样使用VGG-16网络结构,与R-CNN相比训练时间快9倍,测试时间快213倍,准确率从62%提升至66%(再Pascalvoc数据集上)。FastR-CNN主要是解决R-CNN存在的问题:测试训练速度慢,主要是提取候选区域的特征慢:R-CNN首先从测试图中提取2000个候选区域,然后将这2000个候选区域分别输入到预训练好的CNN中提取特征

    2025年10月2日
    2
  • Java Object转JSONObject[通俗易懂]

    Java Object转JSONObject[通俗易懂]JSONObjectjson=(JSONObject)JSONObject.toJSON(list.get(0));

    2022年4月27日
    622
  • Hunyuan-MT-7B保姆级教程:RTX 4080上FP8量化部署全流程

    Hunyuan-MT-7B保姆级教程:RTX 4080上FP8量化部署全流程

    2026年3月12日
    2

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号