Stream流与Lambda表达式(一) 杂谈

42次阅读

共计 13545 个字符,预计需要花费 34 分钟才能阅读完成。

一、流 转换为数组、集合
package com.java.design.java8.Stream;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Stream;

/**
* @author 陈杨
*/

@SpringBootTest
@RunWith(SpringRunner.class)
public class ListChange {

private Stream<String> stream = Stream.of(“Kirito”, “Asuna”, “Illyasviel”, “Sakura”);

@Test
public void testListChange() {

// 将流转换为数组
// System.out.println(“————- 将流转换为数组 —————“);
// String[] array = stream.toArray(len -> new String[len]);
// String[] array = stream.toArray(String[]::new);
// Arrays.asList(array).stream().forEach(System.out::println);

// 将流转换为集合
// System.out.println(“————- 将流转换为集合 —————“);
// System.out.println(“——-Collectors.toList() 解析 ———–“);
/* public static <T>
* Collector<T, ?, List<T>> toList() {
* return new CollectorImpl<>((Supplier<List<T>>) ArrayList::new, List::add,
* (left, right) -> {left.addAll(right); return left; },
* CH_ID);
}*/

// List<String> list = stream.collect(Collectors.toList());
// List<String> linkedList = stream.collect(LinkedList::new,LinkedList::add,LinkedList::addAll);
List<String> list = stream.collect(ArrayList::new, ArrayList::add, ArrayList::addAll);
list.forEach(System.out::println);
System.out.println(list.getClass());

// System.out.println(“——-Collectors.toCollection() 解析 —–“);

/* public static <T, C extends Collection<T>>
* Collector<T, ?, C> toCollection(Supplier<C> collectionFactory) {
* return new CollectorImpl<>(collectionFactory, Collection<T>::add,
* (r1, r2) -> {r1.addAll(r2); return r1; },
* CH_ID);
}*/

// List<String> list =stream.collect(Collectors.toCollection(ArrayList::new));
// List<String> linkedList =stream.collect(Collectors.toCollection(ArrayList::new));
// Set<String> treeSet =stream.collect(Collectors.toCollection(TreeSet::new));
// Set<String> hashSet =stream.collect(Collectors.toCollection(HashSet::new));

}

}
. ____ _ __ _ _
/\\ / ___’_ __ _ _(_)_ __ __ _ \ \ \ \
(()\___ | ‘_ | ‘_| | ‘_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| |) ) ) )
‘ |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.1.2.RELEASE)

2019-02-20 15:47:22.310 INFO 1348 — [main] com.java.design.java8.Stream.ListChange : Starting ListChange on DESKTOP-87RMBG4 with PID 1348 (started by 46250 in E:\IdeaProjects\design)
2019-02-20 15:47:22.311 INFO 1348 — [main] com.java.design.java8.Stream.ListChange : No active profile set, falling back to default profiles: default
2019-02-20 15:47:22.947 INFO 1348 — [main] com.java.design.java8.Stream.ListChange : Started ListChange in 0.914 seconds (JVM running for 1.774)
Kirito
Asuna
Illyasviel
Sakura
class java.util.ArrayList
二、集合排序
package com.java.design.java8.Stream;

import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import java.util.*;

/**
* @author 陈杨
*/

@SpringBootTest
@RunWith(SpringRunner.class)
public class ComparatorDetail {

private List<String> names;

@Before
public void init() {
names = Arrays.asList(“Kirito”, “Asuna”, “Sinon”, “Yuuki”, “Alice”);
}

public void println() {
System.out.println(names);
System.out.println(“—————————————–\n”);
}

@Test
public void testComparatorDetail() {

// 对名字进行升序排序
Collections.sort(names);
this.println();

// 对名字进行降序排序
names.sort(Collections.reverseOrder());
this.println();

// 按照姓名的字符串长度升序排序 相同长度 –> 比较前两个字符 –> 按照字符的 ASCII 码大小升序排序
names.sort(Comparator.comparingInt(String::length)
.thenComparing(str -> str.charAt(0))
.thenComparing(str -> str.charAt(1))
);
this.println();

// 按照姓名的字符串长度降序排序 相同长度 –> 比较前两个字符 –> 按照字符的 ASCII 码大小降序排序
names.sort(Comparator.comparingInt(String::length)
.thenComparing(str -> str.charAt(0))
.thenComparing(str -> str.charAt(1))
.reversed());
this.println();

// 按照姓名的字符串长度降序排序 相同长度 –> 按照字符的 ASCII 码大小排序 (不区分大小写)
names.sort(Comparator.comparingInt(String::length)
.thenComparing(String.CASE_INSENSITIVE_ORDER));
this.println();

}
}
. ____ _ __ _ _
/\\ / ___’_ __ _ _(_)_ __ __ _ \ \ \ \
(()\___ | ‘_ | ‘_| | ‘_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| |) ) ) )
‘ |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.1.2.RELEASE)

2019-02-20 15:58:39.959 INFO 4588 — [main] c.j.d.java8.Stream.ComparatorDetail : Starting ComparatorDetail on DESKTOP-87RMBG4 with PID 4588 (started by 46250 in E:\IdeaProjects\design)
2019-02-20 15:58:39.962 INFO 4588 — [main] c.j.d.java8.Stream.ComparatorDetail : No active profile set, falling back to default profiles: default
2019-02-20 15:58:40.459 INFO 4588 — [main] c.j.d.java8.Stream.ComparatorDetail : Started ComparatorDetail in 0.729 seconds (JVM running for 1.462)
[Alice, Asuna, Kirito, Sinon, Yuuki]
—————————————–

[Yuuki, Sinon, Kirito, Asuna, Alice]
—————————————–

[Alice, Asuna, Sinon, Yuuki, Kirito]
—————————————–

[Kirito, Yuuki, Sinon, Asuna, Alice]
—————————————–

[Alice, Asuna, Sinon, Yuuki, Kirito]
—————————————–
三、Stream 之 map(Lambda)
package com.java.design.java8.Stream;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;

/**
* @author 陈杨
*/

@SpringBootTest
@RunWith(SpringRunner.class)
public class StringOperation {

private List<String> list = Arrays.asList(“Kirito”, “Asuna”, “Illyasviel”, “Sakura”);

private List<List<String>> listMap =
Arrays.asList(Collections.singletonList(“Kirito”), Collections.singletonList(“Asuna”),
Collections.singletonList(“Illyasviel”), Collections.singletonList(“Sakura”));

private List<List<String>> listFlatMap =
Arrays.asList(Collections.singletonList(“Kirito”), Collections.singletonList(“Asuna”),
Collections.singletonList(“Illyasviel”), Collections.singletonList(“Sakura”));

@Test
public void testStringOperation() {

// 集合中 每个字符串 按照排列先后顺序拼接 形成一个长字符串
// String concat =
// list.stream().collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();

// String concat = list.stream().collect(Collectors.joining());
// System.out.println(concat);

// 集合中 对每个字符串元素 将所有字母变成大写字母
System.out.println(“—————————————–\n”);
List<String> upperCase = list.stream().map(String::toUpperCase).collect(Collectors.toList());
upperCase.forEach(System.out::println);

// 集合中 对每个字符串元素 将所有字母变成小写字母
System.out.println(“—————————————–\n”);
List<String> lowerCase = list.stream().map(String::toLowerCase).collect(Collectors.toList());
lowerCase.forEach(System.out::println);

System.out.println(“—————————————–\n”);
System.out.println(“FlatMap 与 Map 的区别:\n”);

// map: 对多个 list 分别 map Fuction 映射 形成多个 list
System.out.println(“—————————————–\n”);
System.out.println(“ 进行 map 映射:”);

List<List<String>> upperMap = listMap.stream()
.map(list -> list.stream().map(String::toUpperCase)
.collect(Collectors.toList())).collect(Collectors.toList());
upperMap.forEach(System.out::println);

// FlatMap:对多个 list 进行 flat 扁平化 后再进行 map Fuction 映射 形成一个 list
System.out.println(“—————————————–\n”);
System.out.println(“FlatMap 扁平化进行 map 映射:”);

List<String> upperFlatMap = listFlatMap.stream()
.flatMap(list -> list.stream().map(String::toUpperCase)).collect(Collectors.toList());
upperFlatMap.forEach(System.out::println);

}
}
. ____ _ __ _ _
/\\ / ___’_ __ _ _(_)_ __ __ _ \ \ \ \
(()\___ | ‘_ | ‘_| | ‘_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| |) ) ) )
‘ |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.1.2.RELEASE)

2019-02-20 15:50:07.423 INFO 8208 — [main] c.j.design.java8.Stream.StringOperation : Starting StringOperation on DESKTOP-87RMBG4 with PID 8208 (started by 46250 in E:\IdeaProjects\design)
2019-02-20 15:50:07.424 INFO 8208 — [main] c.j.design.java8.Stream.StringOperation : No active profile set, falling back to default profiles: default
2019-02-20 15:50:07.917 INFO 8208 — [main] c.j.design.java8.Stream.StringOperation : Started StringOperation in 0.717 seconds (JVM running for 1.5)
—————————————–

KIRITO
ASUNA
ILLYASVIEL
SAKURA
—————————————–

kirito
asuna
illyasviel
sakura
—————————————–

FlatMap 与 Map 的区别:

—————————————–

进行 map 映射:
[KIRITO]
[ASUNA]
[ILLYASVIEL]
[SAKURA]
—————————————–

FlatMap 扁平化进行 map 映射:
KIRITO
ASUNA
ILLYASVIEL
SAKURA
四、内部迭代与外部迭代
package com.java.design.java8.Stream;

import com.java.design.java8.entity.Student;
import com.java.design.java8.entity.Students;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import java.util.*;

/**
* @author 陈杨
*/

@SpringBootTest
@RunWith(SpringRunner.class)
// 迭代本质
public class IterativeEssence {

private List<Student> students;

@Before
public void init() {
students = new Students().init();
}

@Test
public void testIterativeEssence() {

// 需求:select name from students where age > 14 and addr =”Sword Art Online” order by id desc ;

// 外部迭代
System.out.println(“—————————————–\n”);
System.out.println(“ 外部迭代 ”);
List<Student> list = new ArrayList<>();

for (Student student : students) {
if (student.getAge() > 14 && student.getAddr().equals(“Sword Art Online”)) {
list.add(student);
}
}

list.sort(Comparator.comparingInt(Student::getId));

for (Student student : list) {
System.out.println(student.getName());
}

// 内部迭代
System.out.println(“—————————————–\n”);
System.out.println(“ 内部迭代 ”);
students.stream()
.filter(student -> student.getAge() > 14)
.filter(student -> student.getAddr().equals(“Sword Art Online”))
.sorted(Comparator.comparingInt(Student::getId)).
forEach(student -> System.out.println(student.getName()));

// 备注:
// 内部迭代与 SQL 语句属于描述性语言
// 集合关注的是数据与数据存储
// 流关注的是数据的计算
// 流中间操作返回的都是 Stream 对象 泛型取决于中间操作的类型
// 流终止操作:无返回值(forEach)返回值是其他类型
}

}
. ____ _ __ _ _
/\\ / ___’_ __ _ _(_)_ __ __ _ \ \ \ \
(()\___ | ‘_ | ‘_| | ‘_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| |) ) ) )
‘ |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.1.2.RELEASE)

2019-02-20 15:53:03.633 INFO 8864 — [main] c.j.d.java8.Stream.IterativeEssence : Starting IterativeEssence on DESKTOP-87RMBG4 with PID 8864 (started by 46250 in E:\IdeaProjects\design)
2019-02-20 15:53:03.640 INFO 8864 — [main] c.j.d.java8.Stream.IterativeEssence : No active profile set, falling back to default profiles: default
2019-02-20 15:53:04.167 INFO 8864 — [main] c.j.d.java8.Stream.IterativeEssence : Started IterativeEssence in 0.746 seconds (JVM running for 1.455)
—————————————–

外部迭代
Kirito
Asuna
—————————————–

内部迭代
Kirito
Asuna
五、串行流与并行流 简单性能测试
package com.java.design.java8.Stream;

import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.UUID;
import java.util.concurrent.TimeUnit;
import java.util.function.Function;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

/**
* @author 陈杨
*/

@RunWith(SpringRunner.class)
@SpringBootTest
public class ErgodicString {

private List<String> uuid;
private long startTime;
private long endTime;
private long parallelEndTime;

@Before
public void init() {

uuid = new ArrayList<>(10000000);

IntStream.range(0, 10000000).forEach(i -> uuid.add(UUID.randomUUID().toString()));

}

public void testNormal() {

startTime = System.nanoTime();
uuid.stream().sorted().collect(Collectors.toList());

endTime = System.nanoTime();
long millis = TimeUnit.NANOSECONDS.toMillis(endTime – startTime);
System.out.println(“ 单线程 ” + millis);
}

public void testParallel() {

startTime = System.nanoTime();
uuid.parallelStream().sorted().collect(Collectors.toList());
parallelEndTime = System.nanoTime();
long millis = TimeUnit.NANOSECONDS.toMillis(parallelEndTime – startTime);
System.out.println(“ 多线程 ” + millis);
}

@Test
public void testErgodicString() {

List<String> list = Arrays.asList(“Kirito”, “Asuna”, “Illyasviel”, “Sakura”);

// 需求:将数组中每个元素各个字母大写 并放入集合

System.out.println(“——————– 串行流 stream———————“);
// spliterator 分割迭代器
// 串行流 stream() 单线程处理
/*
* default Stream<E> stream() {
* return StreamSupport.stream(spliterator(), false);}
*/

// List<String> collect = list.stream().map(str -> str.toUpperCase()).collect(Collectors.toList());

// R apply(T t); toUpperCase() 没有参数作为输入
// 但把调用 toUpperCase 的对象作为 T 作为输入 返回的 R 是 return 的对象结果
// List<String> collect = list.stream().map(String::toUpperCase).collect(Collectors.toList());

Function<String, String> function = String::toUpperCase;

// 等价于 (String str) -> str.toUpperCase()
// 方法引用 类的类型:: 实例方法 对应的 lambda 表达式 第一个输入参数 是调用此方法的对象
List<String> collect = list.stream().map(function).collect(Collectors.toList());

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

this.testNormal();

System.out.println(“—————– 并行流 parallelStream——————“);
// 并行流 parallelStream() 多线程处理
/*
* default Stream<E> parallelStream() {
* return StreamSupport.stream(spliterator(), true);}
*/

List<String> parallelCollect = list.parallelStream().map(str -> str.toUpperCase()).collect(Collectors.toList());
parallelCollect.forEach(System.out::println);

this.testParallel();

}

}
. ____ _ __ _ _
/\\ / ___’_ __ _ _(_)_ __ __ _ \ \ \ \
(()\___ | ‘_ | ‘_| | ‘_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| |) ) ) )
‘ |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v2.1.2.RELEASE)

2019-02-20 15:54:54.321 INFO 7356 — [main] c.j.design.java8.Stream.ErgodicString : Starting ErgodicString on DESKTOP-87RMBG4 with PID 7356 (started by 46250 in E:\IdeaProjects\design)
2019-02-20 15:54:54.323 INFO 7356 — [main] c.j.design.java8.Stream.ErgodicString : No active profile set, falling back to default profiles: default
2019-02-20 15:54:54.817 INFO 7356 — [main] c.j.design.java8.Stream.ErgodicString : Started ErgodicString in 0.705 seconds (JVM running for 1.528)
——————– 串行流 stream———————
KIRITO
ASUNA
ILLYASVIEL
SAKURA
单线程 10590
—————– 并行流 parallelStream——————
KIRITO
ASUNA
ILLYASVIEL
SAKURA
多线程 3313

正文完
 0