Stream流
1. 单列集合的Stream流获取
package com.wz.stream01;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.function.Consumer;
import java.util.function.Predicate;
import java.util.stream.Stream;
public class streamDemo {
public static void main(String[] args) {
//源
List numbers = Arrays.asList(1,2,3,4,5);
//通过源获取Stream流
Stream stream = numbers.stream();
//对源中的数据进行过滤
// stream.filter(new Predicate() {
// @Override
// public boolean test(Integer integer) {
// return integer>3;
// }
// });
Stream integerStream = stream.filter(integer -> integer > 3);
//遍历剩下的元素
// integerStream.forEach(new Consumer() {
// @Override
// public void accept(Integer integer) {
// System.out.println(integer);
// }
// });
integerStream.forEach(System.out::println);
System.out.println("------------------");
HashSet set = new HashSet<>();
set.add('a');
set.add('b');
set.add('c');
set.add('d');
set.add('e');
set.add('f');
set.stream().filter(character -> character>'c').forEach(System.out::println);
}
}
在代码中,首先创建了一个包含整数的列表
numbers
,然后通过numbers.stream()
获取了一个Stream
流。接着,使用
filter
方法对流中的元素进行过滤。使用了 lambda 表达式来简化过滤条件的定义,只保留大于 3 的元素。然后,使用
forEach
方法遍历过滤后的元素并打印出来。使用了方法引用System.out::println
使用 Stream 流对字符集合进行过滤和遍历。首先创建了一个包含字符的 HashSet 集合
set
,然后使用set.stream()
获取了一个流。接着,使用filter
方法过滤出大于字符 'c' 的元素,并使用forEach
方法遍历并打印出来。
2. 双列集合及数组的Stream流获取
双列集合无法直接获取Stream流对象,只有先拿到单列集合,然后再获取Stream流对象
Stream
> stream =map.entrySet().stream(); Stream stream = map.keySet().stream() 数组获取Stream流对象通过Arrays工具类获取
String[] names = {"ZhangSan","LiSi","WangWu"}; Stream
stream1 = Arrays.stream(names); 数组还可以通过Stream流自身提供的of方法来获取
Stream
stream2 = Stream.of("ZhangSan", "LiSi", "WangWu");
package com.wz.stream01;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
import java.util.stream.Stream;
public class streamDemo02 {
public static void main(String[] args) {
HashMap map = new HashMap<>();
map.put("ZhangSan", 20);
map.put("LiSi", 21);
map.put("WangWu", 22);
//双列集合无法直接获取Stream流对象,只有先拿到单列集合,然后再获取Stream流对象
// Stream> stream = map.entrySet().stream();
Stream stream = map.keySet().stream()c
//数组获取Stream流对象通过Arrays工具类获取
String[] names = {"ZhangSan","LiSi","WangWu"};
Stream stream1 = Arrays.stream(names);
//数组还可以通过Stream流自身提供的of方法来获取
Stream stream2 = Stream.of("ZhangSan", "LiSi", "WangWu");
//将多个Stream流中的元素拼接到一起,形成一个新的Stream流
Stream concat = Stream.concat(stream1, stream2);
}
}
3. 使用 Stream 流对一个用户数组进行操作。
package com.wz.stream02;
public class User {
String username;
String password;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
@Override
public String toString() {
return "User{" +
"username='" + username + '\'' +
", password='" + password + '\'' +
'}';
}
}
package com.wz.stream02;
import java.util.Arrays;
import java.util.Random;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.stream.Stream;
public class UserDemo {
private static final char[] CHARACTERS = {
'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z'
};
public static void main(String[] args) {
//初始化数组
User[] users = new User[10];
for (int i = 0; i < 10; i++) {
User user = new User();
user.setUsername(randomStr(5));
user.setPassword(randomStr(10));
users[i]=user;
}
// Stream stream = Arrays.stream(users).map(new Function() {
// @Override
// public String apply(User user) {
// return user.getUsername();
// }
// });
// stream.forEach(new Consumer() {
// @Override
// public void accept(String s) {
// System.out.println(s);
// }
// });
Arrays.stream(users).map(User::getUsername).forEach(System.out::println);
}
//自定义随机字符
private static String randomStr(int length){
StringBuilder builder = new StringBuilder();
Random r = new Random();
for (int i = 0 ; i
使用 Stream 流对一个用户数组进行操作。
首先,代码定义了一个包含小写字母的字符数组
CHARACTERS
。接下来,代码创建了一个用户数组
users
,并使用循环为每个用户对象设置用户名和密码。然后,代码展示了如何使用 Stream 流从用户数组中提取用户名并打印出来:
- 使用
Arrays.stream(users)
将用户数组转换为流。- 使用
map
方法将流中的每个用户对象映射为其用户名。通过Arrays.stream(users).map(User::getUsername)
将用户数组中的每个用户对象转换为其用户名。- 使用
forEach
方法遍历流中的每个用户名,并使用System.out.println
打印出来。通过Arrays.stream(users).map(User::getUsername).forEach(System.out::println)
对流中的每个用户名执行打印操作。最后,代码使用自定义的
randomStr
方法生成随机字符串,用于设置用户的用户名和密码。
4. Stream流中间聚合操作
Stream filter(Predicate super T> predicate);//根据给定的条件过滤流中的元素
Stream map(Function super T, ? extends R> mapper);//将流中元素进行类型转换
Stream distinct();//去重
Stream sorted();//排序,如果存储元素没有实现Comparable或者相关集合没有提供Comparator将抛出异常
Stream limit(long maxSize);//根据给定的上限,获取流中的元素
Stream skip(long n);//跳过给定数量的元素
IntStream mapToInt(ToIntFunction super T> mapper);//将流中元素全部转为整数
LongStream mapToLong(ToLongFunction super T> mapper);//将流中元素全部转为长整数
DoubleStream mapToDouble(ToDoubleFunction super T> mapper);//将流中元素全部转为双精度浮点数
package com.wz.stream03;
import java.util.Comparator;
import java.util.stream.Stream;
public class StreamOperation {
public static void main(String[] args) {
Stream s = Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50);
//distinct()可以对管道中的元素进行去重
s.distinct().forEach(System.out::println);
System.out.println("-------------------------");
Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50)
//排序,默认是升序排序,如果需要进行降序排列,需要给定一个
//排序器进行降序排列
.sorted()
.forEach(System.out::println);
System.out.println("-------------------------");
Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50)
.sorted((o1, o2) -> o2-o1)
.forEach(System.out::println);
System.out.println("-------------------------");
Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50)
//limit()限制管道中的元素个数
.limit(5)
.forEach(System.out::println);
System.out.println("-------------------------");
Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50)
.skip(6)
.forEach(System.out::println);
}
}
- 使用
distinct
方法对流中的元素进行去重。通过s.distinct().forEach(System.out::println)
去重并打印每个元素。- 使用
sorted
方法对流中的元素进行排序。默认情况下,排序是升序的。通过Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50).sorted().forEach(System.out::println)
进行升序排序并打印每个元素。- 如果需要进行降序排列,可以给定一个自定义的排序器。通过
Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50).sorted((o1, o2) -> o2-o1).forEach(System.out::println)
进行降序排序并打印每个元素。- 使用
limit
方法限制流中元素的个数。通过Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50).limit(5).forEach(System.out::println)
限制流中只有前 5 个元素,并打印每个元素。- 使用
skip
方法跳过流中的前几个元素。通过Stream.of(10, 50, 64, 12, 46, 23, 41, 36,10,50).skip(6).forEach(System.out::println)
跳过前 6 个元素,并打印剩余的元素。
package com.wz.stream03;
import java.util.Arrays;
import java.util.function.ToIntFunction;
import java.util.stream.IntStream;
public class StreamOperation02 {
public static void main(String[] args) {
//使用Stream流进行数据类型转换
Integer[] numbers = {1,2,3,4};
// IntStream intStream = Arrays.stream(numbers).mapToInt(new ToIntFunction() {
// @Override
// public int applyAsInt(Integer value) {
// return value.intValue();
// }
// });
// IntStream intStream = Arrays.stream(numbers).mapToInt(Integer::intValue);
// int[] array = intStream.toArray();
int[] array = Arrays.stream(numbers).mapToInt(Integer::intValue).toArray();
System.out.println(Arrays.toString(array));
}
}
如何使用 Stream 流进行数据类型转换:
首先,代码创建了一个整数数组
numbers
。
- 使用
Arrays.stream(numbers)
将整数数组转换为流。- 使用
mapToInt
方法将流中的元素映射为int
类型。通过Arrays.stream(numbers).mapToInt(Integer::intValue)
将整数数组中的每个元素转换为对应的int
值。- 使用
toArray
方法将流中的元素转换为int
数组。通过Arrays.stream(numbers).mapToInt(Integer::intValue).toArray()
将流中的元素转换为int
数组。最后,代码使用
Arrays.toString(array)
将转换后的int
数组转换为字符串,并输出结果。
package com.wz.stream03;
import java.util.Arrays;
import java.util.function.IntFunction;
import java.util.stream.Stream;
public class StreamOperation03 {
public static void main(String[] args) {
Integer[] numbers = {1, 2, 3, 4};
int[] array = Arrays.stream(numbers).mapToInt(Integer::intValue).toArray();
System.out.println(Arrays.toString(array));
Stream boxed = Arrays.stream(array).boxed();
// boxed.toArray(new IntFunction() {
// @Override
// public Integer[] apply(int value) {
// return new Integer[value];
// }
// });
// boxed.toArray(value -> new Integer[value]);
Integer[] array1 = boxed.toArray(Integer[]::new);
}
}
利用Stream 流将整数数组转换为基本类型
int
数组:
- 使用
Arrays.stream(numbers)
将整数数组转换为流。- 使用
mapToInt
方法将流中的元素映射为int
类型。通过Arrays.stream(numbers).mapToInt(Integer::intValue)
将整数数组中的每个元素转换为对应的int
值。- 使用
toArray
方法将流中的元素转换为int
数组。通过Arrays.stream(numbers).mapToInt(Integer::intValue).toArray()
将流中的元素转换为int
数组。使用 Stream 流将基本类型
int
数组转换为包装类型Integer
数组:
- 使用
Arrays.stream(array)
将基本类型int
数组转换为流。- 使用
boxed
方法将流中的元素包装为对应的包装类型Integer
。通过Arrays.stream(array).boxed()
将基本类型int
数组中的每个元素转换为对应的包装类型Integer
。- 使用
toArray
方法将流中的元素转换为Integer
数组。通过boxed.toArray(Integer[]::new)
将流中的元素转换为Integer
数组。
5. Stream流终结操作
void forEach(Consumer super T> action);//遍历操作流中元素
A[] toArray(IntFunction generator);//将流中元素按照给定的转换方式转换为数组
R collect(Collector super T, A, R> collector);//将流中的元素按照给定的方式搜集起来
Optional min(Comparator super T> comparator);//根据给定的排序方式获取流中最小元素
Optional max(Comparator super T> comparator);//根据给定的排序方式获取流中最大元素
Optional findFirst(); //获取流中第一个元素
long count();//获取流中元素数量
boolean anyMatch(Predicate super T> predicate);//检测流中是否存在给定条件的元素
boolean allMatch(Predicate super T> predicate);//检测流中元素是否全部满足给定条件
boolean noneMatch(Predicate super T> predicate);//检测流中元素是否全部不满足给定条件
package com.wz.stream04;
import java.util.*;
import java.util.function.Predicate;
import java.util.stream.Collectors;
import java.util.stream.Stream;
public class StreamTerminal {
private static final char[] CHARACTERS = {
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'
};
public static void main(String[] args) {
//初始化数组
List users = new ArrayList<>();
for (int i = 0; i < 10; i++) {
User user = new User();
user.setUsername(randomStr(5));
user.setPassword(randomStr(10));
System.out.println(user);
}
User user = new User();
user.setUsername("admin");
user.setPassword("123456");
String username = "admin";
users.add(user);
System.out.println(username);
// users.stream().map(User::getUsername).forEach(System.out::println);
//过滤
Stream stream = users.stream().filter(u -> u.getUsername().equals(username));
//将流中的元素按照给定的方式搜集起来,我们指定的收集方式是收集为一个List集合。
List userList = stream.collect(Collectors.toList());
//set集合
// Set uesrSet = stream.collect(Collectors.toSet());
//数组
// User[] array = stream.toArray(User[]::new);
if (userList.size() > 0) {
System.out.println(username + "已经被注册了");
}
//检测流中是否存在给定条件的元素
// users.stream().anyMatch(new Predicate() {
// @Override
// public boolean test(User user) {
// return user.getUsername().equals(username);
// }
// });
if (users.stream().anyMatch(user1 -> user1.getUsername().equals(username))) {
System.out.println(username + "已经被注册了");
}
//检测流中元素是否全部不满足给定条件
// users.stream().noneMatch(new Predicate() {
// @Override
// public boolean test(User user) {
// return user.getUsername().equals(username);
// }
// });
if (users.stream().noneMatch(user2 -> user2.getUsername().equals(username))) {
System.out.println(username + "可以注册");
}
//检测流中元素是否全部满足给定条件
// users.stream().allMatch(new Predicate() {
// @Override
// public boolean test(User user) {
// return user.getUsername().length() >=5;
// }
// });
if (users.stream().allMatch(user12 -> user12.getUsername().length() >= 5)) {
System.out.println("所有用户的用户名长度均>=5");
}
Integer[] numbers = {1, 2, 3, 4, 5,};
//count()一般在filter之后才会调用
long count = Arrays.stream(numbers).filter(num -> num > 3).count();
System.out.println(count);
//求最值的时候必须要给定一个比较器,因为Stream流支持的是泛型,具体是
//什么类型需要根据使用的情况来确定,而这个类型不一定是可比较的,因此,
//需要我们提供比较的方式。最值得到的结果存储在一个容器中,这个容器是
//是一个比较特殊的容器,这个容器至多存储一个值(可能一个值都没有)
//根据给定的排序方式获取流中最小元素
// Optional opt = users.stream().min(new Comparator() {
// @Override
// public int compare(User o1, User o2) {
// return o1.getUsername().compareTo(o2.getUsername());
// }
// });
Optional opt = users.stream().min((o1, o2) -> o1.getUsername().compareTo(o2.getUsername()));
//users.stream().min(Comparator.comparing(User::getUsername));
User u = opt.orElse(null);
System.out.println(u);
}
private static String randomStr(int length) {
StringBuilder builder = new StringBuilder();
Random r = new Random();
for (int i = 0; i < length; i++) {
int index = r.nextInt(CHARACTERS.length);
builder.append(CHARACTERS[index]);
}
return builder.toString();
}
}
- 使用
collect
方法将流中的元素收集到一个List
集合中。通过users.stream().filter(u -> u.getUsername().equals(username))
过滤出用户名与指定值相等的用户流,然后使用collect(Collectors.toList())
将流中的元素收集为一个列表。- 使用
anyMatch
方法检测流中是否存在满足给定条件的元素。通过users.stream().anyMatch(user1 -> user1.getUsername().equals(username))
判断是否有用户名与指定值相等的用户。- 使用
noneMatch
方法检测流中是否所有元素都不满足给定条件。通过users.stream().noneMatch(user2 -> user2.getUsername().equals(username))
判断是否所有用户名都与指定值不相等。- 使用
allMatch
方法检测流中是否所有元素都满足给定条件。通过users.stream().allMatch(user12 -> user12.getUsername().length() >= 5)
判断是否所有用户名长度都大于等于 5。- 使用
count
方法统计流中满足给定条件的元素个数。通过Arrays.stream(numbers).filter(num -> num > 3).count()
统计数组中大于 3 的元素个数。- 使用
min
方法获取流中的最小元素。通过users.stream().min((o1, o2) -> o1.getUsername().compareTo(o2.getUsername()))
获取用户名最小的用户对象。注意,这里使用了 lambda 表达式作为比较器。