java进阶(Stream流,综合小案例)
Stream流
-
可以用于操作集合或者数组的数据。
-
简化集合,数组操作的API,结合了Lambda表达式。
-
不用流接收数据,最后会把Stream操作的结果转回到一个数组或者集合中去返回
-
流只能收集一次
-
处理步骤为:
- 先得到集合或者数组的Stream流
- 如何调用Stream流的方法对数据进行处理
- 获取处理的结果
-
举例:
import java.util.ArrayList; import java.util.List; import java.util.stream.Collectors; public class Test { public static void main(String[] args) { List<String> list = new ArrayList<>(); list.add("张三"); list.add("李四"); list.add("张乐乐"); list.add("吴飞"); list.add("张牛牛"); //1.传统方法,找出姓张的人,并且名字为3个字的,存入到一个新集合里面 List<String> list1 = new ArrayList<>();//新的集合 for (String s : list) { if(s.startsWith("张")&&s.length()==3){ list1.add(s); } } System.out.println(list1); //2.Stream流方法 //定义一个新集合存储数据,其中filter为过滤某个条件,collect为收集数据 List<String> list2=list.stream().filter(s->s.startsWith("张")).filter(s->s.length()==3).collect(Collectors.toList()); System.out.println(list2); } } -
获取Stream流:
-
获取集合的Stream流(单列Collection集合)
Collection<String> list =new ArrayList<>(); Stream<String> s1 = list.stream(); -
获取集合的Stream流(双列Map集合)
Map<String,String> map =new HashMap<>(); //获取键流 Stream<String> s2 = map.keySet().stream(); //获取值流 Stream<String> s3 = map.values().stream(); //获取键值对流 Stream<Map.Entry<String, String>> s4 = map.entrySet().stream(); -
获取数组的流
//获取数组的流 String[] str={"a","b","c","d","e","f"}; Stream<String> s5=Arrays.stream(str); System.out.println(a5.count());//6,取的是个数 Stream<String> s6 = Stream.of(str);//Steam.of();里面可以设置任意类型的可变参数。
-
-
Stream常用的方法:
//1.过滤方法 list.stream().filter(s->s.startsWith("张")&&s.length()==3).forEach(System.out::println); //2.排序方法 List<Double> list1 = new ArrayList<>(); list1.add(54.5); list1.add(23.4); list1.add(65.7); list1.add(88.6); list1.add(88.6); list1.stream().sorted().forEach(System.out::println);//默认升序 list1.stream().sorted((s1,s2)->Double.compare(s2,s1)).forEach(System.out::println);//重写sort方法变成降序 //只要前两个数字 list1.stream().sorted().limit(2).forEach(System.out::println); //跳过前两名 list1.stream().sorted().skip(2).forEach(System.out::println); //去重,要是是引用类型对象,就要重写hashCode和equals方法 list1.stream().distinct().forEach(System.out::println); //加工方法(映射方法),把流上原来的数据拿出来变成新数据又放到流上去 list1.stream().map(s->"加十分后:"+(s+10)).forEach(System.out::println); //合并流 Stream<String> s1 = Stream.of("qq","www","fdds","jjj"); Stream<Integer> s2 = Stream.of(2,33,43,12,4); Stream<Object> stream = Stream.concat(s1,s2);//合并这两个流 stream.forEach(System.out::println); -
Stream流的终结方法:
- void forEach();//遍历
- long count();//统计个数
- Optional max((t1,t2)->Double.compare(t1.getSum( ),t2.getSum( )));//取最大值,Optional为容器。
- Optional min((t1,t2)->Double.compare(t1.getSum( ),t2.getSum( )));//取最小值
//收集流到List集合中去,例: Stream<String>s1=list.stream().filter(s->s.startsWith("张")); List<String> ll=s1.collect(Collectors.toList()); //收集流到Set集合中去,例: Set<String> ss=s1.collect(Collectors.toSet()); //收集流到数组中去,例: Object[] ch=s1.toArray(); //收集流到Map集合中去,将老师名字作为键,老师薪水作为值例: Map<String,Double> map=teachers.stream().collect(Collectors.toMap(Teacher::getName,Teacher::getSalary)); -
可变参数:
public class Test3 { public static void main(String[] args) { sum(); sum(10); sum(12,23,43);//实际传入的是数组 } //可变参数在形参列表中只能有一个,并且放在最后面 public static void sum(int ...nums) { System.out.println(Arrays.toString(nums)); } }
综合小案例
- 斗地主的做牌,洗牌,发牌,对牌进行排序
package CardsDemo;
import java.util.*;
public class Service {
//创建一个牌容器
List<Card> cards = new ArrayList<>();
//定义牌的花色和数字,还有大小
String[] color = {"♥", "♦", "♠", "♣"};
String[] number = {"3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K", "A","2"};
//创建一个方法来开始牌局
public void start() {
int size=0;//定义一个size来设定牌的大小
//将花色和数字拼接存入牌堆
for (int i = 0; i < number.length; i++) {
size++;
for (int j = 0; j < color.length; j++) {
cards.add(new Card(number[i], color[j],size));
}
}
//利用Collections方法来添加大小王
Collections.addAll(cards, new Card("🃏", "",14), new Card("👲", "",15));
System.out.println(cards.toString());
//洗牌
System.out.println("洗牌后牌堆为:");
Collections.shuffle(cards);
System.out.println(cards.toString());
//定义三个玩家及其手上的牌存入Map集合
Map<String, List<Card>> player = new HashMap<>();
//第一个玩家
List<Card> l1 = new ArrayList<>();
player.put("小白", l1);
//第二个玩家
List<Card> l2 = new ArrayList<>();
player.put("阿飞", l2);
//第三个玩家
List<Card> l3 = new ArrayList<>();
player.put("小雨", l3);
//遍历牌堆进行发牌,留下三张给地主的牌
for (int i = 0; i < cards.size() - 3; i++) {
if (i % 3 == 0) {
l1.add(cards.get(i));
}
if (i % 3 == 1) {
l2.add(cards.get(i));
}
if (i % 3 == 2) {
l3.add(cards.get(i));
}
}
//把最后的三张牌发给地主
//存储最后三张牌
List<Card> lastCards = cards.subList(cards.size() - 3, cards.size());
//用随机数模拟谁抢到了地主
Random r = new Random();
int temp = r.nextInt(lastCards.size());
String str="";
switch (temp) {
case 0:
l1.addAll(lastCards);
str="小白";
break;
case 1:
l2.addAll(lastCards);
str="阿飞";
break;
case 2:
l3.addAll(lastCards);
str="小雨";
break;
}
System.out.println(str+"抢到了地主");
//对每个人手里的牌进行排序
player.forEach((k,v)->{
sortCards(v);
});
//查看每个人手里的牌
player.forEach((k, v) -> {
System.out.println(k + "的牌为:" + v);
});
}
//一个排序的方法
private void sortCards(List<Card> cards) {
Collections.sort(cards, new Comparator<Card>() {
@Override
public int compare(Card o1, Card o2) {
return o1.getSize()-o2.getSize();
}
});
}
}
//牌类
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class Card {
private String color;
private String number;
private int size;
@Override
public String toString() {
return color + number ;
}
}
//测试类:
public class Game {
public static void main(String[] args) {
//1.创建一个桌面来进行斗地主游戏
Service service = new Service();
service.start();
}
}
//结果为:
[3♥, 3♦, 3♠, 3♣, 4♥, 4♦, 4♠, 4♣, 5♥, 5♦, 5♠, 5♣, 6♥, 6♦, 6♠, 6♣, 7♥, 7♦, 7♠, 7♣, 8♥, 8♦, 8♠, 8♣, 9♥, 9♦, 9♠, 9♣, 10♥, 10♦, 10♠, 10♣, J♥, J♦, J♠, J♣, Q♥, Q♦, Q♠, Q♣, K♥, K♦, K♠, K♣, A♥, A♦, A♠, A♣, 2♥, 2♦, 2♠, 2♣, 🃏, 👲]
洗牌后牌堆为:
[4♦, 10♠, K♦, J♦, 7♠, 6♣, 4♠, 8♥, K♥, J♣, 9♣, 10♦, 5♠, K♠, 2♥, 9♥, 5♣, 6♥, 8♦, 3♠, 3♣, 2♦, 7♦, 9♦, 5♥, 8♠, 8♣, 3♦, A♣, 7♥, 3♥, A♦, Q♣, 10♥, A♥, 5♦, Q♠, 👲, 9♠, J♥, Q♥, 🃏, J♠, 6♦, 2♣, A♠, Q♦, 4♣, 2♠, 7♣, K♣, 4♥, 10♣, 6♠]
阿飞抢到了地主
小雨的牌为:[3♣, 4♣, 5♦, 6♣, 6♥, 7♥, 8♣, 9♦, 9♠, 10♦, Q♣, K♦, K♥, K♣, 2♥, 2♣, 🃏]
小白的牌为:[3♦, 3♥, 4♦, 4♠, 5♠, 5♥, 8♦, 9♥, 10♥, J♦, J♣, J♥, J♠, Q♠, A♠, 2♦, 2♠]
阿飞的牌为:[3♠, 4♥, 5♣, 6♦, 6♠, 7♠, 7♦, 7♣, 8♥, 8♠, 9♣, 10♠, 10♣, Q♥, Q♦, K♠, A♣, A♦, A♥, 👲]
浙公网安备 33010602011771号