概念
流(Stream)与集合类似,但集合中保存的是数据,而Stream中保存对集合或数组数据的操作。
特点
- tream 自己不会存储元素。
- Stream 不会改变源对象。相反,他们会返回一个持有结果的新Stream。
- Stream 操作是延迟执行的,会等到需要结果的时候才执行。
使用
创建:
- 新建一个流。
中间操作:
- 在一个或多个步骤中,将初始Stream转化到另一个Stream的中间操作。
终止操作:
- 使用一个终止操作来产生一个结果。该操作会强制之前的延迟操作立即执行,在此之后,该Stream就不能使用了。
创建方式:
- 通过Collection对象的stream()或parallelStream()方法。
- 通过Arrays类的stream()方法。
- 通过Stream接口的of()、iterate()、generate()方法。
- 通过IntStream、LongStream、DoubleStream接口中的of、range、rangeClosed方法。
创建
List<String> list=new ArrayList<>();
list.add("111");
list.add("222");
list.add("33");
//获取stream对象1
Stream<String> stream = list.stream();
stream.forEach(System.out::println);
//获取stream对象2
Stream<String> stringStream = Stream.of("222", "444", "555");
stringStream.forEach(System.out::println);
中间操作:
//中间操作
//filter 过滤 传入参数是一个断言型接口 获取集合中长度大于2的元素
list.stream().filter(s -> s.length() > 2).forEach(System.out::println);
//limit 和mysql的limit相似 获取集合的前1条数据
list.stream().limit(1).forEach(System.out::println);
//distinct 去重
list.stream().distinct().forEach(System.out::println);
//sorted 排序 传入一个比较器 和list的sort方法相似 将集合元素按长度从小到大排序
list.stream().sorted((o1,o2)->o1.length()-o2.length());
//map 传入一个函数型接口 将集合中的元素全部转换成Int型
list.stream().map(Integer::parseInt).forEach(System.out::println);
//parallel 使用多线程操作集合中的元素
list.stream().parallel().forEach((s)->{
System.out.println(Thread.currentThread().getName()+" "+s);
});
终止操作:
//终止操作
//min 获取集合中最小元素 最小的判断是按照比较器来的 就是输出经过比较器排序后的第一个元素
Optional<String> min = list.stream().min((o1, o2) -> {
return o1.length() - o2.length();
});
System.out.println(min.get());
//max 获取集合中最大元素 与min机制相同 是输出最后一个
Optional<String> max = list.stream().max((o1, o2) -> {
return o1.length() - o2.length();
});
System.out.println(max.get());
//count 计数 获取长度为3的元素的个数
long count = list.stream().filter(s -> s.length() == 3).count();
System.out.println(count);
//reduce 将元素转换为int并求和
list.stream().map(Integer::parseInt).reduce(0,(o1,o2)->o1+o2);
//collect 将stream流对象转换为List Set Map集合 将流转换为list
List<String> collect = list.stream().collect(Collectors.toList());
collect.forEach(System.out::println);
常见函数式接口
- Consumer 消费型接口 参数为T 返回void ;
void accept(T t)对类型为T的对象应用操作
public class MyConsumer {
public static void test(String str, Consumer<String> consumer){
consumer.accept(str);
}
public static void main(String[] args) {
MyConsumer.test("hello",str-> System.out.println(str));
test("hello",System.out::println);
}
}
- Supplier 供给型接口
参数无 返回值为T
T get();返回类型为T的对象
public class MySupplier {
public static void main(String[] args) {
System.out.println(test(() -> {
return "hello";
}));
}
public static String test(Supplier<String> supplier){
return supplier.get();
}
}
3.Function<T,R>函数型接口
参数T 返回值R
R apply(T t) 对类型为T的对象应用操作,并返回类型为R类型的对象
public class MyFunction {
public static void main(String[] args) {
System.out.println(test("hello", str -> {
return str;
}));
}
public static String test(String s, Function<String,String> f){
return f.apply(s);
}
}
4.Predicate 断言型接口
参数T 返回值boolean
boolean test(T t);确定类型为T的对象是否满足条件 满足返回true
public class Predicate {
public static void main(String[] args) {
System.out.println(test("hello", str -> {
return "hello".equals(str);
}));
}
public static boolean test(String s, java.util.function.Predicate<String> p){
return p.test(s);
}
}