Lambda 简单用例

package com.lambda.demo;

import com.lambda.demo.exception.CanNotGetUserExceptionSupplier;
import com.lambda.demo.model.User;
import com.lambda.demo.model.UserSupplier;
import org.junit.Test;

import java.util.*;
import java.util.function.BinaryOperator;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * Stream 简单操作
 * https://www.ibm.com/developerworks/cn/java/j-lo-java8streamapi/
 *
 * @author Jake.Woo
 * <p>
 * Stream 操作简单介绍:
 * 每一个Stream 中的数据只能被使用一次.所以Stream API 大体可以分为两种操作类型:
 * 1. intermediate (中间操作) 不会立即产生结果的操作.
 * map (mapToInt, flatMap 等)、 filter、 distinct、
 * sorted、 peek、 limit、 skip、 parallel、 sequential、 unordered
 * 2. terminal (最终操作) 每个Stream 只能有一个Terminal 操作
 * forEach、 forEachOrdered、 toArray、 reduce、 collect、 min、
 * max、 count、 anyMatch、 allMatch、 noneMatch、 findFirst、 findAny、 iterator
 * 当切仅当Terminal 性质的API 被调用的时候,Stream 中的数据才会被真正的使用
 * 类似于,StringBuffer 的append 和toString 方法 toString 时,才会生成想要的String 对象
 * 还有一种针对无限大的Stream 做过滤的操作,在无限大的Stream 中获取一个新的有限的Stream
 * anyMatch、 allMatch、 noneMatch、 findFirst、 findAny、 limit
 */
public class StreamDemo {

    /**
     * reduction :
     * 通过{@link java.util.stream.Collectors} 辅助
     */
    @Test
    public void reductionDemo() {
        //归档--按照user age 进行归档 返回结果key 为age value 为age 下的集合
        Map<Integer, List<User>> collect =
                Stream.generate(new UserSupplier()).limit(100)
                        .collect(Collectors.groupingBy(User::getAge));
        collect.forEach((age, user) -> System.out.println("age:" + age + ", user:" + user));


        //分片. 年龄大于等于十八岁的,年龄小于十八岁的
        Map<Boolean, List<User>> collect1 =
                Stream.generate(new UserSupplier()).limit(100)
                        .collect(Collectors.partitioningBy(user -> user.getAge() > 18));
        collect1.forEach((age, user) ->
                System.out.println("age > 18:" + age
                        + ", user:" + user.size()));
    }

    /**
     * iterate 接受一个初始值 和一个运算规则 生成Stream
     */
    @Test
    public void iterateDemo() {
        //等差数列
        Stream.iterate(0, n -> n + 3)
                .limit(10)
                .forEach(System.out::println);
    }

    /**
     * 生成流,需要limit 限制数量
     */
    @Test
    public void generateDemo() {
        Random random = new Random();
        List<Integer> collect = Stream
                .generate(random::nextInt)
                .limit(13).sorted()
                .peek(num -> System.out.println(num + ", "))
                .skip(5).collect(Collectors.toList());

        collect.forEach(System.out::println);

        Stream.generate(new UserSupplier())
                .limit(5).peek(System.out::println)
                .collect(Collectors.toList());

    }

    /**
     * allMatch: Stream 中所有元素都满足 返回true
     * anyMatch: 有一个满足 返回true
     * noneMatch: 没有一个元素满足 返回true
     */
    @Test
    public void matchDemo() {
        System.out.println(
                "all user age > 18? "
                        + userStream().allMatch(user -> user.getAge() > 18));
        System.out.println(
                "there is a user age = 18? "
                        + userStream().anyMatch(user -> user.getAge() == 18));
        System.out.println(
                "not a user age < 18? "
                        + userStream().noneMatch(user -> user.getAge() < 18));
    }

    /**
     * 过滤.唯一
     */
    @Test
    public void distinctDemo() {
        Stream.of("abc", "def", "acb", "abc", "def")
                .distinct().
                map(String::toLowerCase)
//                .sorted()
                .collect(Collectors.toList())
                .forEach(System.out::println);
    }

    @Test
    public void maxDemo() {
        System.out.println(
                Stream.of(3, 2, 1, 6, 5, 7, 9, 4)
                        .max(Integer::compareTo)
                        .get());
    }

    @Test
    public void minDemo() {
        System.out.println(
                Stream.of(3, 2, 1, 6, 5, 7, 9, 4)
                        .min(Integer::compareTo)
                        .get());
    }

    /**
     * 对流中的数据进行排序
     */
    @Test
    public void sortedDemo() {
        Stream.of(3, 1, 2, 6, 5, 7, 9, 4)
                .sorted().forEach(System.out::println);
        System.out.println("------");
        userStream().sorted((user1, user2) -> user2.getAge()
                .compareTo(user1.getAge())).forEach(System.out::println);
    }

    /**
     * limit: 返回Stream 前面几个元素
     * skip: 扔掉前面几个元素
     */
    @Test
    public void limitAndSkipDemo() {
        Stream.of(3, 1, 2, 6, 5, 7, 9, 4).limit(5).forEach(System.out::println);
        System.out.println("-----");
        Stream.of(3, 1, 2, 6, 5, 7, 9, 4).skip(2).forEach(System.out::println);
    }

    /**
     * reduce 将stream 中的数据做合并,最终返回一个结果
     */
    @Test
    public void reduceDemo() {
        //一个参数 参数为数据处理方式 返回结果是一个optional 实例
        Stream<Integer> integerStream = integerStream();
        Integer integer = integerStream.reduce((a, b) -> a + b).get();
        System.out.println(integer);
        //两个参数: 第一个参数为初始元素,如果stream 中没有元素,则返回初始元素
        //如果有元素,则初始元素将参与运算
        Stream<Integer> integerStream2 = Stream.of(0);
        Integer reduce = integerStream2.reduce(-1, (a, b) -> a + b);
        System.out.println(reduce);
        //三个参数: 基本与两个参数类似
        //第三个参数针对的是并行操作涉及到的结果集的处理
        //非并行模式,第三个参数不会被调用到
        ArrayList<User> userList =
        userStream().reduce(
            new ArrayList<User>(), (list, user) -> {
                list.add(user);
                return list;
            }, new BinaryOperator<ArrayList<User>>() {
                @Override
                public ArrayList<User> apply(ArrayList<User> list1,
                                             ArrayList<User> list2) {
                    System.out.println("我调用了这个方法");
                    return list1;
                }
            });
        userList.forEach(System.out::println);
        //并行模式下,第三个参数是对并行模式下数据归并的处理逻辑
        Integer reduce1 =
                Stream.of(1, 2, 3, 4, 5).parallel()
                        .reduce(4, (a, b) -> a + b, (c, d) -> c + d);
        System.out.println(reduce1);
        //最后结果为35, 因为并行处理,且线程间的独立性.使得每个元素都被加了identity
        //因此最后的结果为所有元素都加了identity 之后的和
    }

    /**
     * 获取Stream 第一个元素,或者空
     */
    @Test
    public void findFirstDemo() {
        Stream<User> userStream = userStream();
        Optional<User> first = userStream.findFirst();
        System.out.println(first.orElseThrow(new CanNotGetUserExceptionSupplier()));
        System.out.println(userStream.findAny().get());
    }

    /**
     * 流转换为对象
     */
    @Test
    public void transitionDemo() {

        Stack<Integer> intStack =
                integerStream()
                        .collect(Collectors.toCollection(Stack::new));
        intStack.forEach(System.out::println);

        Set<String> stringSet =
                stringStream().collect(Collectors.toSet());
        stringSet.forEach(System.out::println);

        User[] userArr = userStream().toArray(User[]::new);
        Arrays.stream(userArr).forEach(System.out::println);
    }

    /**
     * Map操作: 将Stream 中的元素按照传入的规则映射成新的元素
     * emmmm... 不是我们理解的那个Map 集合 只是表示一种映射操作
     */
    @Test
    public void mapDemo() {
        Stream<Integer> stream = integerStream();
        stream.map(num -> num * 100).forEach(System.out::println);
    }

    /**
     * flatMap :将Stream 中的多个对象,合并成一个对象
     */
    @Test
    public void flatMapDemo() {
        Stream<List<Integer>> listStream =
                Stream.of(Arrays.asList(1, 3, 5), Arrays.asList(2, 4, 6));
        listStream.flatMap(Collection::stream).forEach(System.out::print);
        //listStream.flatMap(list->list.stream()).forEach(System.out::print);
    }

    /**
     * Filter 将数据按照条件进行过滤
     */
    @Test
    public void filterDemo() {
        userStream().filter(user -> user.getAge() == 21)
                .forEach(System.out::println);
    }

    /**
     * peek 对每个元素进行操作,但是不是立即执行.遇到Terminal 操作时,才会逐一对元素执行所有的peek 操作
     */
    @Test
    public void peekDemo() {
        userStream().peek(System.out::println).filter(user -> user.getName().length() > 1)
                .peek(user -> user.setAge(user.getAge() + 10)).forEach(System.out::println);
    }

    /**
     * 创建一个user Stream 对象
     *
     * @return
     */
    public Stream<User> userStream() {
        List<User> list = new ArrayList<>();

        list.add(new User("张三", 21));
        list.add(new User("李四", 33));
        list.add(new User("王五", 18));
        return list.stream();
        //并行流
//        return list.stream().parallel();
//        return list.parallelStream();
    }


    /**
     * 创建一个String Stream 对象
     *
     * @return
     */
    public Stream<String> stringStream() {
        String[] arr = new String[]{"张三", "李四",
                "王五", "赵六", "周扒皮", "靓妹", "帅哥"};
        return Arrays.stream(arr);
//        return Stream.of(arr);
    }

    /**
     * 创建一个 integer Stream 对象
     *
     * @return
     */
    public Stream<Integer> integerStream() {
        return Stream.of(1, 11, 22, 3, 44, 5, 32, 51, 66);
    }
}
package com.lambda.demo;

import com.lambda.demo.exception.CanNotGetUserExceptionSupplier;
import com.lambda.demo.model.User;
import com.lambda.demo.model.UserSupplier;
import org.junit.Test;

import java.util.ArrayList;
import java.util.List;
import java.util.Optional;

/**
 * @author Jake.Woo
 * optional 主要解决NPE 问题
 * 大概包含如下API
 * 创建一个Optional of ofNullable
 * 判断是否有实例数据 isPresent
 * 获取实例 get orElse orElseGet orElseThrow
 * 对实例进行操作 map flatMap
 * 过滤 filter
 */
public class OptionalDemo {
    /**
     * flatMap
     * 操作和{@link #mapDemo()}类似 但是返回结果是Optional 类型
     */
    @Test
    public void flatMap() {
        Optional<String> stringOptional = Optional.of("aBcDeFg");
//        Optional<String> stringOptional = Optional.empty();
        System.out.println(stringOptional
                .flatMap(val -> Optional.of(val.substring(0, 3)))
                .orElse("no value"));
        System.out.println(stringOptional
                .map(val -> val.substring(0, 3))
                .orElse("no value"));
    }

    /**
     * map
     * 对optional 内的元素进行操作,
     * 如果元素为空,不做处理并返回null
     */
    @Test
    public void mapDemo() {
        Optional<String> stringOptional = Optional.of("aBcDeFg");
//        Optional<String> stringOptional = Optional.empty();
        System.out.println(
                stringOptional.map(String::toUpperCase)
                        .orElse("no value"));
    }

    /**
     * filter
     */
    @Test
    public void filterDemo() {
        Optional<String> stringOptional = Optional.of("abcde");
        System.out.println("过滤之后,是否还有数据: "
                + stringOptional.filter(val -> val.length() > 3)
                .isPresent());
    }

    /**
     * orElseThrow
     * 获取一个实例.如果没有, 通过实现supplier 接口的自定义异常,获取一个异常抛出
     */
    @Test
    public void orElseThrowDemo() {
        System.out.println(Optional.empty()
                .orElseThrow(
                        new CanNotGetUserExceptionSupplier()));
    }

    /**
     * orElseGet
     * 获取对象.如果没有,通过supplier 获取一个实例
     */
    @Test
    public void orElseGetDemo() {
        Optional<User> objectOptional = Optional.empty();
        System.out.println(objectOptional.orElseGet(new UserSupplier()));
    }

    /**
     * orElse 如果不存在,返回传入的对象
     */
    @Test
    public void orElseDemo() {
        Optional<Object> objectOptional = Optional.of("我是初始值");
        System.out.println(objectOptional.orElse("没有值得时候.返回值就是我"));
        System.out.println("---------");
        objectOptional = Optional.empty();
        System.out.println(objectOptional.orElse("没有值得时候.返回值就是我"));
    }

    /**
     * get 如果值为null 抛出异常
     * NoSuchElementException: No value present
     * 否则,返回该值
     */
    @Test
    public void getDemo() {
        Optional<Object> objectOptional = Optional.of(new Object());
        System.out.println(objectOptional.get());

        Optional<Object> empty = Optional.empty();
        System.out.println(empty);
        System.out.println(empty.get());
    }

    /**
     * 返回一个值为null的 Optional
     */
    @Test
    public void emptyDemo() {
        Optional<Object> empty = Optional.empty();
        empty.ifPresent(System.out::println);
        System.out.println("Optional is Present: " + empty.isPresent());

    }

    /**
     * isPresent 是否存在(是否不为空)
     */
    @Test
    public void isPresentDemo() {
        Optional<Integer> optAsNull = Optional.ofNullable(null);
        System.out.println("optAsNull: " + optAsNull.isPresent());
        Optional<Integer> opt = Optional.of(1);
        System.out.println("optNotNull: " + opt.isPresent());
    }

    /**
     * if Present 如果存在,做点什么
     */
    @Test
    public void ifPresentDemo() {
        //ifPresent 如果存在,就做点什么.
        List<Integer> list = new ArrayList<>();
        Optional.of(1).ifPresent(list::add);
        Optional.of(10).ifPresent(list::add);
        //如果不存在,不进行操作
        Optional.ofNullable(null).ifPresent(val->{
            System.out.println(val);
            list.add((Integer) val);
        });
        System.out.println("-----");
        list.forEach(System.out::println);
    }

    /**
     * 三种创建方式
     */
    @Test
    public void createDemo(){
        //of : 必须有值且不为null
        Optional.of(10);
        //ofNullable : 必须有值,可以为null
        Optional.ofNullable(null);
        //empty : 创建一个值为null 的实例
        Optional.empty();
    }
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值