Java1.8新特性 Stream 多线程

本文介绍了Java8及以上版本的新特性,包括接口中静态方法、默认方法、私有方法的变化,以及四大内置函数式接口(Consumer、Function、Predicate、Supplier)。此外,还详细讲解了方法引用、Stream流的使用、多线程和Callable接口的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、jdk1.8接口新增内容

静态方法:static   只能根据类名调用

默认方法:被default修饰得方法 

                 实现类调用使用     可以在实现类中重写

jdk1.9新增

私有方法:被private修饰得方法 

                   只能在当前接口中使用,接口中的默认方法可以调用   

二、四大内置函数式接口

函数式接口 :    java.util.function下的函数式接口

四大内置函数式接口 :
1.消费型接口        Consumer<T>   void accept(T t)
2.函数式接口        Function<T,R> R apply(T t)
3.段言型接口        Predicate<T>boolean test(T t)
4.供给型接口        Supplier<T>T get()

public class Class001_FunctionalInterface {
    public static void main(String[] args) {
        happy(5000,m-> System.out.println("为PDD刷火箭消费"+m));
        happy(10000,m-> System.out.println("买包消费"+m));

        System.out.println(strHandler("DLGJGL",s->s.toLowerCase()));

        System.out.println(test(10,()->(int)(Math.random()*(8-5+1)+5)));
    }

    //消费
    public static void happy(double money, Consumer<Double> con){
        con.accept(money);
    }

    //对任意一个 字符串进行某种操作返回结果
    public static String strHandler(String str, Function<String,String> fun){
        return fun.apply(str);
    }

    //生成指定个数的指定规则的随机整数
    public static List<Integer> test(int num, Supplier<Integer> sup){
        List<Integer> list = new ArrayList<>();
        for(int i=1;i<=num;i++){
            list.add(sup.get());
        }
        return list;
    }

}

三、方法引用

方法引用:用来简化Lambda表达式

简化条件要求 : 必须满足一下2个条件
1.当lambda体{}中的实现就是通过调用另外一个方法实现的,可以考虑是否可以通过方法引用简化
2.
        a)当lambda参数列表,返回值与内部引用方法的参数列表与返回值保持一致的时候 ---->

对象:: 成员方法 | 类名::静态方法

         b)内部所引用方法的 返回值与lambda表达式的返回值一致,
                lambda参数列表的第一个参数作为调用内部方法的对象,
                lambda参数列表的第二个参数开始匹配内部引用方法参数列表 ----> 类名::成员方法

public class Class002_Quite {
    public static void main(String[] args) {
        //对象::成员方法
        List<Integer> list = List.of(1,2,3,4,5);

        //分析 : 1. 满足   println()        2)  a)满足   ===>对象::成员方法
        /*list.forEach(i->{
            System.out.println(i);
        });*/
        list.forEach(System.out::println);

        Map<String,Integer> map = Map.of("aaa",3,"bb",2);

        map.forEach((k,v)->System.out.println(k+"--->"+v));

        //类名::静态方法
        //求两个double中的最大值
        //BiFunction<Double,Double,Double> fun = (x,y)->Math.max(x,y);
        //分析  : 1. 满足  max()  2.a)满足 ===>类名::静态方法
        BiFunction<Double,Double,Double> fun = Math::max;

        System.out.println(fun.apply(1.1,2.2));;

        //类名::成员方法
        //比较两个字符串是否相等
        //BiPredicate<String,String> bi = (x,y)->x.equals(y);
        //分析  : 1. 满足  equals  2. b) 类名::成员方法
        BiPredicate<String,String> bi = String::equals;

        System.out.println(bi.test("nihao",new String("nihao")));;

    }
}

四、Stream

IO流 : 关注数据的传输
集合|数组 : 关注数据的存储
Stream流 : 关注数据的运算         将由数据源产生的元素序列进行流式运算

使用步骤:

1.获取创建Stream   2.一系列流式中间操作    3.终止行为

特点

1.Stream本身不能存储数据   

2.Stream的运算不影响数据源

3.所有中间操作都返回持有结果的新的流

4.流是一次性的流,一旦已经使用就被破坏,无法重复使用多次

5.延迟执行|惰性加载:当获取终止行为的时候所有的中间操作才会执行

获取Sream的方式

1.Collection-->stream()   2.Arrays.stream()  3.Stream.of(...)

Stream中间操作 :
1.过滤 <T> filter(Predicate<? super T> predicate) 返回由与给定谓词匹配的此流的元素组成的流。
2.截取 Stream<T> limit(long maxSize) 返回由该流的元素组成的流,长度被截断为不超过maxSize 。
3.跳过 Stream<T> skip(long n) 在丢弃流的前n元素后,返回由该流的剩余元素组成的流。
4.去重 Stream<T> distinct() 返回由该流的不同元素(根据Object.equals(Object) )组成的流。
根据equals与hashCode方法,需要根据内容重写

5.排序
Stream<T> sorted() 返回由该流的元素组成的流,按自然顺序排序。
Stream<T> sorted(Comparator<? super T> comparator) 返回由该流的元素组成的流,根据提供的Comparator排序。

6.映射 : 将流操作的每一个元素映射成为另外一种结果 | 提取信息

map : 将参数函数应用与此流的所有元素 ,映射成为不同的结果,最后返回持有所有结果的新的流
<R> Stream<R> map(Function<? super T,? extends R> mapper) 返回由将给定函数应用于此流的元素的结果组成的流。

flatMap :
<R> Stream<R> flatMap(Function<? super T,? extends Stream<? extends R>> mapper)
返回一个流,其中包含将此流的每个元素替换为通过将提供的映射函数应用于每个元素而生成的映射流的内容的结果。

map与 flatMap :
1.映射结果类型的要求不同
        map : 映射结果没有类型要求,可以为任意类型,包括私有
        flatMap : 映射的结果必须为一个流,不能为其他类型
2.映射结果返回流的结构不同
        map : 返回持有所有映射结果的新的流 ,如果映射结果为一个流,最终返回的Stream<Stream>
        flatMap :在返回之前先对所有映射结果流进行连接,连接成为一个流返回

终止行为:

遍历 :  void forEach(Consumer<? super T> action)   对此流的每个元素执行一个操作。
查找
        Optional<T> findAny() 返回描述流的某些元素的Optional ,如果流为空,则返回空的Optional 。
        Optional<T> findFirst() 返回描述此流的第一个元素的Optional ,如果流为空,则返回空的Optional 。
匹配
        boolean noneMatch(Predicate<? super T> predicate) 返回此流的任何元素是否与提供的谓词匹配。
        boolean allMatch(Predicate<? super T> predicate) 返回此流的所有元素是否与提供的谓词匹配。
        boolean anyMatch(Predicate<? super T> predicate) 返回此流的任何元素是否与提供的谓词匹配。

统计 
        long count() 返回此流中元素的计数。
        Optional<T> max(Comparator<? super T> comparator) 根据提供的Comparator返回此流的最大元素。
        Optional<T> min(Comparator<? super T> comparator) 根据提供的Comparator返回此流的最小元素。
规约
        Optional<T> reduce(BinaryOperator<T> accumulator) 使用associative累积函数对此流的元素执行reduction ,并返回Optional描述减少的值(如果有)。
        T reduce(T identity, BinaryOperator<T> accumulator) 使用提供的标识值和associative累积函数对此流的元素执行reduction ,并返回减少的值。

收集
collect ,收集,可以说是内容最繁多、功能最丰富的部分了。
从字面上去理解,就是把一个流收集起来,最终可以是收集成一个值也可以收集成一个新的集合。
collect 主要依赖 java.util.stream.Collectors 类内置的静态方法。

<R, A> R collect(Collector<? super T,A,R> collector) 使用Collector对此流的元素执行mutable reduction操作。

五、多线程

多线程Thread:多任务执行,多路径执行   线程是程序中的执行顺序流

Java虚拟机允许应用程序同时运行多个执行程序

线程和进程的区别:

 多线程的优点:资源利用率更好,性能更高,效率更高

多线程的缺点:设计复杂,可能造成数据不安全

线程的创建方式:

 1.继承Thread,重写run方法 + start开启线程

public class Thread001 extends Thread{
    //1.继承Thread,重写run方法+start开启线程
    @Override
    public void run(){
        for(int i=0;i<=100;i++){
            System.out.println("一边喝水");
            //切换时间
            try {
                Thread.sleep(1);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
        }
    }

    public static void main(String[] args) {
        //主线程
        //创建主线程对象
        Thread001 th=new Thread001();
        //开启线程(准备好了)
        th.start();
        for(int i=0;i<=100;i++){
            System.out.println("一遍讲课");
            try {
                Thread.sleep(1);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
        }

    }
}

 2.实现Runnable接口,重写run方法 + start开启线程

public class Thread002 implements Runnable{
    //票数
    int tickets=100;
    @Override
    public void run() {
        while(true){
            if(tickets<=0){
                break;
            }
            System.out.println(Thread.currentThread().getName()+"正在购票"+tickets--+"张票..");
            try {
                Thread.sleep(1);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
        }


    }

    public static void main(String[] args) {
        //一趟车次
        Thread002 wab=new Thread002();
        //三个线程
        Thread th1=new Thread(wab,"zhangsan");
        Thread th2=new Thread(wab,"lisi");
        Thread th3=new Thread(wab,"wangwu ");
        //开启线程
        th1.start();
        th2.start();
        th3.start();
    }
}

 3.实现juc包下Callable接口,重写call方法 + 线程池 

//3.实现juc包下Callable接口,重写call方法+线程池
//优点:可以抛出异常  带出返回值
//龟兔赛跑比赛
public class Thread003 implements Callable {
    String winner=null;

    @Override
    public Object call()  {
        for(int i=1;i<=100;i++){
            System.out.println(Thread.currentThread().getName()+"正在跑第"+i+"步");
            try {
                Thread.sleep(1);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
            if("pool-1-thread-1".equals(Thread.currentThread().getName())&&i%10==0){
                try {
                    Thread.sleep(1);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
            if(!check(i)){
                return i;
            }
        }
        return null;
    }
    public boolean check(int steps){
        if(winner!=null){
            return false;
        }
        if(steps==100){
            winner=Thread.currentThread().getName();
            return false;
        }
        return true;
    }

    public static void main(String[] args) throws ExecutionException, InterruptedException {
        //创建比赛
        Thread003 match=new Thread003();
        //创建线程池服务
        ExecutorService server= Executors.newFixedThreadPool(2);
        //提交任务

        Future<Integer> f1=server.submit(match);
        Future<Integer> f2=server.submit(match);
        //获取结果
        System.out.println(f1.get());
        System.out.println(f2.get());
        //关闭线程池服务
        server.shutdown();

    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值