一篇搞定Lambda和Stream流
一、Lambda表达式
jdk8中的语法糖,优化某些匿名内部类的写法,函数式编程的重要体现,不再关注对象是什么,更关注数据进行了什么操作
1、练习
练习1
练习2
练习3
练习4
练习5
2、省略规则
- 参数类型可以省略
- 方法体只有一句代码时大括号return和那句代码的分号可以省略
- 方法还有一个参数时小括号可以省略
- 不知道怎么省略就直接Alt+回车
二、Stream流
使用的是函数式编程模式,如同名字一样,可以被用来对集合或数组进行链状流式的操作,更方便我们对集合或数组操作
1、入门案例
把集合中年龄小于18的作家名字打印,注意去掉重复的
注意:所有中间方法的调用离不开终结方法,如果没有调用终结方法,中间都不会执行
2、创建操作
单列集合:直接.stream()就行
数组:Stream<Integer> stream = Arrays.stream(arr);还有一种方式就是使用Stream类的of方法传入一个数组也是得到一个流对象
双列集合:用map调用entrySet方法转化为set集合,set集合存放的就是entry,一个entry包含key和value。转化为单列集合后再调用单列集合的方法。
3、中间操作
filter
对流中国的元素进行条件过滤,符合过滤条件的才能进行留在流中
例如:打印所有名字长度大于1的作家的姓名
map
可以把流当中元素进行计算或者转化
例如:打印所有作家的名字
获得到所有作家的年龄然后加10打印
distinct
可以去除流中重复元素
例如:打印所有作家的名字,并且要求其中不能有重复元素
注意:distinct方法是依赖Object的equals方法来判断是否是相同对象的,所以需要注意重写equals方法
sorted
可以对流中的元素进行排序
例如:对流中国元素按照年龄进行降序排序,并且要求不能有重复的元素。
如果调用空参数的sorted方法,需要流中的元素是实现comparable接口的
用带参数的也可以,直接传入匿名内部类的形式
limit
可以设置流的最大长度,超出的部分将背抛弃
skip
跳过流中前n个元素,返回剩下的元素
例如:打印除了年龄最大的作家外的其他作家,要求不能有重复元素,并且按照年龄降序排序
flatMap
map只能把一个对象转化成另一个对象来作为流中的元素,而flatMap可以把一个对象转化成多个对象作为流中的元素
例一:一个作者写了很多书,打印所有书籍的名字,要求对重复元素进行去重
flatMap会帮我们把一个对象转化为多个对象放到流中
例一:打印现有数据所有分类,要求分类进行去重,不能出现这种格式:哲学,爱情
第二个flatMap方法中的split分割完是数组,数组转化为stream就得用Arrays的api
4、终结操作
forEach
对流中的元素进行遍历操作,通过传入参数指定对遍历的元素进行什么操作
count
可以用来获取流中元素的个数
例子:打印作家的所有书籍的数目,注意删除重复元素
max&min
可以用来获取流中的最值
例子:分别获取作家书籍中最高分和最低分并打印
collect
把当前流转换成一个集合
anyMatch
是否有满嘴条件的,如果有就返回true,所有元素都不符合返回false
allMatch
判断是否所有的都匹配,如果是返回true,不是返回false
noneMatch
都不符合返回true,有符合的就返回false
findAny
获取流中任意一个符合条件的元素,改方法不能保证获取的一定是流中的第一个元素
optional是jdk为了防止接收的空指针所有规定要用这个返回
findFirst
获取流中第一个符合条件的元素
reduce
对流中的数据按照你指定的计算方式计算出一个结果(缩减操作)
reduce的作用就是把流中的元素组合起来,我们可以传入初始值,他会按照我们计算方式依次拿六中元素和初始值的基础上进行计算,计算结果再和后面的元素计算
5、注意事项
惰性求值(如果没终结操作,没中间操作是不会得到执行的)
流是一次性的(一旦一个流对象经过一个终结操作后,这个流就不能再被使用了)
不会影响原数据(流中可以多数据做处理,正常下不会影响原来集合中的数据)