Stream像操做SQL同样处理数据,因此很概念很是相近,能够对比着理解 。html
分为静态建立和实例建立,不一样的方法适用于不一样场景。目的都是为了转成流java
/** * 初始 * <p> * 适用于数组和简单的数据转为stream * </p> */ @Test public void test_static_of() { Stream.of(Person.builder().name("name").age(1)); /** * 打印的是list的元素 */ Stream.of(newArray()).forEach(System.out::println); /** * 打印的是list的toString,因此集合不使用该方法 */ Stream.of(newList()).forEach(System.out::println); } /** * 范围 * <p> * 适用于整数迭代 * </p> */ @Test public void test_static_range(){ /** * 不包含10 */ IntStream.range(1,10).forEach(System.out::println); /** * 包含10 */ IntStream.rangeClosed(1,10).forEach(System.out::println); } /** * 生成 * <p> * 适用于批量生成而且赋值 * 好比生成id或者uuid * </p> */ @Test public void test_static_generate() { Stream.generate(UUID::randomUUID) .limit(10) .forEach(System.out::println); Stream.generate(()->Math.random()*1000) .limit(10) .forEach(System.out::println); } @Test public void test_static_iterate() { Stream.iterate(10, index -> { Person.builder().name("name").age(index); return --index; }).limit(10).forEach(System.out::println); } /** * 集合 */ @Test public void test_instance_collection() { /** * 打印的是list的元素 */ newList().stream().forEach(System.out::println); } /** * 正则 */ @Test public void test_regex() { String sentence = "Program creek is a Java site."; Pattern.compile("\\W").splitAsStream(sentence).forEach(System.out::println); } /** * 文件 * @throws IOException */ @Test public void test_file() throws IOException { String fileName = "c://lines.txt"; Files.lines(Paths.get(fileName)).forEach(System.out::println); } private List<String> newList() { List<String> list = new ArrayList<>(); list.add("lisi"); return list; } private String[] newArray() { return new String[]{"sili", "wangwu"}; }
把一个流转为另外一个流,能够不断的转换。包括:过滤,转换,限制,排序,去重。经过不断的转换最终获取目标数据数据库
private Stream<Person> newStream(){ List<Person> list = new ArrayList<>(); list.add(Person.builder().name("zhangsan").age(12).build()); list.add(Person.builder().name("zhangsan").age(12).build()); list.add(Person.builder().name("lisi").age(18).build()); list.add(Person.builder().name("wangwu").age(25).build()); return list.stream(); } /** * 过滤 * <p> * 过滤不符合条件的数据。 * 好比说: * <ul> * <li>结合数据库查询,在java里过滤数据</li> * <li>过滤掉npe</li> * <li>过滤不符合业务数据</li> * </ul> * </p> */ @Test public void test_filter(){ newStream() .filter(person->person.getAge()>=18) .forEach(System.out::println); } /** * 类型转换 * <p> * 用于快速转换数据类型 * 好比说: * <ul> * <li>根据实例快速转出id集合</li> * </ul> * </p> */ @Test public void test_mapper(){ newStream() .map(Person::getId) .forEach(System.out::println); } /** * 限制 * <p> * 取前几个 * </p> */ @Test public void test_limit(){ newStream() .limit(2) .forEach(System.out::println); } /** * 排序 */ @Test public void test_sorted(){ newStream() .sorted((p1,p2)->{ if(p1.getAge()>p2.getAge()){ return 1; }else if (p1.getAge()<p2.getAge()){ return -1; }else{ return 0; } }) .forEach(System.out::println); } /** * 排序 */ @Test public void test_sorted_comparator() { newStream() .sorted(Comparator //排序 .comparing(Person::getAge) //倒序 .reversed() .thenComparing(Person::getName) ) .forEach(System.out::println); } /** * 去重 */ @Test public void test_distinct(){ newStream() .distinct() .forEach(System.out::println); } /** * 综合使用 * <p> * 经过这些计算能够快速找出期待的数据,并且还不须要不断的添加遍历和破坏代码可读性 * </p> */ @Test public void test_combine(){ newStream() .filter(person->null==person) .distinct() .filter(person -> person.getAge()>=18) .map(Person::getAge) .sorted((age1,age2)->{ if(age1>age2){ return 1; }else if (age1<age2){ return -1; }else{ return 0; } }) .limit(1) .forEach(System.out::println); }
一个流只能有一个停止动做。停止后流就不能使用。包括:查找,匹配,循环,统计,类型转换,分组。数组
private Stream<Person> newStream() { List<Person> list = new ArrayList<>(); list.add(Person.builder().name("zhangsan").age(12).build()); list.add(Person.builder().name("zhangsan").age(12).build()); list.add(Person.builder().name("lisi").age(18).build()); list.add(Person.builder().name("wangwu").age(25).build()); return list.stream(); } /** * 查找 * */ @Test public void test_find() { /** * 返回第一个值 */ Optional<Person> first = newStream().findFirst(); Assert.assertEquals(first.get(),newStream().collect(toList()).get(0)); /** * 返回随机值 */ Optional<Person> any = newStream().findAny(); System.out.println(any.get()); } /** * 匹配 */ @Test public void test_match() { Assert.assertTrue(newStream().anyMatch(person -> person.getAge() == 18)); Assert.assertFalse(newStream().allMatch(person -> person.getAge() == 18)); Assert.assertFalse(newStream().noneMatch(person -> person.getAge() == 18)); } /** * 统计 * */ @Test public void test_stat_max() { Optional<Person> maxAge = newStream().max((p1, p2) -> { if (p1.getAge() > p2.getAge()) { return 1; } else if (p1.getAge() < p2.getAge()) { return -1; } else { return 0; } }); System.out.println(maxAge); } /** * 个数 */ @Test public void test_stat_count() { long count = newStream().count(); System.out.println(count); } /** * 循环 */ @Test public void test_forEach() { newStream().forEach(System.out::println); } /** * 归并 */ @Test public void test_reduce() { /** * 第一个参数是上次结果 * 第二个参数是元素 */ Optional<Integer> totalAge = newStream() .map(Person::getAge) .reduce((result, age) -> result + age); System.out.println(totalAge.get()); /** * 第一个参数是初始值 * 第二个参数是上次结果 * 第三个参数是元素 */ Integer totalAgeWithInit = newStream() .map(Person::getAge) .reduce(10, (result, age) -> result + age); System.out.println(totalAgeWithInit); } /** * 转为数组 * */ @Test public void test_toArray(){ newStream().toArray(); } /** * 转为collection */ @Test public void test_toCollection(){ newStream().collect(toList()); newStream().collect(toSet()); } /** * 转为map */ @Test public void test_toMap(){ /** * 第一个参数是key * 第二个参数是value * * <p> * 若是有重复主键时会报错。 * 若是Key为null会报错 * </p> */ //newStream().collect(toMap(Person::getId,person->person)); /** * 第三个参数是若是key重复的时候取哪一个值 */ newStream().collect(toMap(Person::getId,person->person,(oldValue,newValue)->oldValue)); newStream().collect(toMap(Person::getId,person->person,(oldValue,newValue)->newValue)); /** * 返回具体的map实例类型 */ newStream().collect(toMap(Person::getId,person->person,(oldValue,newValue)->oldValue,HashMap::new)); newStream().collect(toMap(Person::getId,person->person,(oldValue,newValue)->oldValue,LinkedHashMap::new)); } /** * 经过分组转为Map * * <p> * 分组完,通常会对元素进行聚合 * </p> */ @Test public void test_toMap_group(){ /** * 不存在重复key报错的问题 */ Map<Long, List<Person>> listMap = newStream().collect(groupingBy(Person::getId)); /** * 可是返回值是double */ Map<Long, Double> averageAgeMap = newStream().collect( groupingBy(Person::getId, averagingLong(Person::getAge)) ); /** * 找出最大年龄对应的Map */ Map<String, Optional<Person>> maxAgeMap = newStream().collect( groupingBy(Person::getName, maxBy(Comparator.comparing(Person::getAge))) ); }
@Test public void test_format() { newStream() .filter(person -> null == person) .distinct() .filter(person -> person.getAge() >= 18) .map(Person::getAge) .sorted((age1, age2) -> { if (age1 > age2) { return 1; } else if (age1 < age2) { return -1; } else { return 0; } }) .limit(1) .forEach(System.out::println); newStream() .filter(person -> null == person) .distinct() .filter(person -> person.getAge() >= 18) .map(Person::getAge) //上面排序超过三行,不容易阅读 .sorted(Comparator.comparing(Long::valueOf)) .limit(1) .forEach(System.out::println); } @Test public void test_single() { newStream() .filter(person -> { if(null != person){ return true; } if(person.getAge() > 18){ return true; } if(person.getName().startsWith("hello")){ return true; } return false; }) ; newStream() .filter(person -> null != person) .filter(person -> person.getAge() > 18) .filter(person -> person.getName().startsWith("hello")) ; }
@Test public void test_forEach() { List<Person> persons = new ArrayList<>(); List<Person> adultPersons = new ArrayList<>(); for (Person person : persons) { if (person.getAge() > 18) { adultPersons.add(person); } } List<Person> adultPersons2 = persons.stream() .filter(person -> person.getAge() > 18) .collect(Collectors.toList()); }
@Test public void test_forEach(){ newStream().forEach(person -> { // 不要在forEach里作过滤的行为 if(person.getAge()>18){ /** * 这里的return就至关于for里的continue,后面的例子仍是会继续的。 * 没法实现break的效果,必定会把全部元素走完 */ return ; } System.out.println(person); }); newStream() .filter(person -> person.getAge()>18) .forEach(System.out::println); }
诚邀,有梦想有激情有实力的小伙伴一块儿加入咱们,改变世界。下面是JD的详情信息并发