java异步编程CompletableFuture使用示例详解

目录
  • 一、简单介绍
  • 二、常见操作
    • 1、使用默认线程池
    • 2、使用自定义线程池
    • 3、获取线程的执行结果
  • 三、处理异步结算的结果
  • 四、异常处理
  • 五、组合 CompletableFuture
  • 六、并行运行多个 CompletableFuture
  • 七、案例
    • 1、从多个平台获取书价格
    • 2、从任意一个平台获取结果就返回

一、简单介绍

CompletableFuture 同时实现了 Future 和 CompletionStage 接口。

public class CompletableFuture<T> implements Future<T>, CompletionStage<T>

CompletableFuture 除了提供了更为好用和强大的 Future 特性之外,还提供了函数式编程的能力。

Future 接口有 5 个方法:

boolean cancel(boolean mayInterruptIfRunning) :尝试取消执行任务。

boolean isCancelled() :判断任务是否被取消。

boolean isDone() : 判断任务是否已经被执行完成。

get() :等待任务执行完成并获取运算结果。

get(long timeout, TimeUnit unit) :多了一个超时时间。

CompletionStage<T> 接口中的方法比较多,CompletableFuture 的函数式能力就是这个接口赋予的。从这个接口的方法参数你就可以发现其大量使用了 Java8 引入的函数式编程。

二、常见操作

1、使用默认线程池

// 使用默认的线程池,ForkJoinPool
CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(()->{
   System.out.println("come in");
   System.out.println("是否为守护线程: " + Thread.currentThread().isDaemon());
   System.out.println("当前线程名称:" + Thread.currentThread().getName());
   try {
       Thread.sleep(2000);
   } catch (InterruptedException e) {
       e.printStackTrace();
   }
   System.out.println("is ending");
   return "hello";
});
System.out.println("I am main thread");

输出如下:

I am main thread
come in
是否为守护线程: true

从输出结果可以看出,使用默认的线程池,启动是线程是守护线程,如果主线程执行完毕,会导致守护线程结束。 导致 is ending 无法输出。

2、使用自定义线程池

ExecutorService executorService = Executors.newFixedThreadPool(3);
// 使用自定义线程池
CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(()->{
    System.out.println("come in");
    System.out.println("是否为守护线程: " + Thread.currentThread().isDaemon());
    System.out.println("当前线程名称:" + Thread.currentThread().getName());
    try {
        Thread.sleep(2000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
    System.out.println("is ending");
    return "hello";
},executorService);
System.out.println("I am main thread");
// 关闭线程池
executorService.shutdown();

输出如下:

I am main thread
come in
是否为守护线程: false
当前线程名称:pool-1-thread-1
is ending

可以看出,使用自定义线程池,创建出来的线程不是守护线程。

3、获取线程的执行结果

1、 get()

会阻塞当前主线程,等待任务线程执行完成,获取任务线程结果

ExecutorService executorService = Executors.newFixedThreadPool(3);
// 使用自定义线程池
CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(()->{
   System.out.println("come in");
   System.out.println("是否为守护线程: " + Thread.currentThread().isDaemon());
   System.out.println("当前线程名称:" + Thread.currentThread().getName());
   try {
       Thread.sleep(2000);
   } catch (InterruptedException e) {
       e.printStackTrace();
   }
   System.out.println("is ending");
   return "hello";
},executorService);
System.out.println("I am main thread");
System.out.println("等待线程执行结束");
// 阻塞等待任务执行完成。
String s = completableFuture.get();
System.out.println("线程执行结果为:" + s);
executorService.shutdown();

输出为:

I am main thread
等待线程执行结束
come in
是否为守护线程: false
当前线程名称:pool-1-thread-1
is ending
线程执行结果为:hello

2、getNow(defaultValue)

如果线程执行完成,获取线程的执行结果,如果没有执行完,获取传递的默认结果值 defaultValue 。

3、whenComplete(BiConsumer<? super T, ? super Throwable> action)

异步回调,获取线程的执行结果。

completableFuture.whenComplete((v,e)->{
    // 没有异常
    if (e == null) {
        System.out.println("执行结果为:" + v);
    }
});

异常返回的处理。

ExecutorService executorService = Executors.newFixedThreadPool(3);
// 使用自定义线程池
CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(()->{
    System.out.println("come in");
    try {
        Thread.sleep(2000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
    int i = 10 / 0;
    return "hello";
},executorService);
completableFuture.whenComplete((v,e)->{
    // 没有异常
    if (e == null) {
        System.out.println("执行结果为:" + v);
    } else {
        System.out.println(e.getMessage());
        System.out.println("异常了,要处理拉");
    }
});
executorService.shutdown();

输出结果如下:

come in
java.lang.ArithmeticException: / by zero
异常了,要处理拉

三、处理异步结算的结果

当我们获取到异步计算的结果之后,还可以对其进行进一步的处理,比较常用的方法有下面几个:

thenApply()

thenAccept()

thenRun()

whenComplete()

thenApply() 方法接受一个 Function 实例,用它来处理结果。

CompletableFuture.supplyAsync(()->{
    return 10;
}).thenApply((s)->{
    return  s + 20;
}).thenApply(s->{
    return s+ 30;
}).whenComplete((v,e)->{
    if (e == null) {
        System.out.println("结果为:" + v);
    }
});
// 等待线程执行完毕
Thread.sleep(2000);

输出结果为:

结果为:60

如果你不需要从回调函数中获取返回结果,可以使用 thenAccept() 或者 thenRun()。这两个方法的区别在于 thenRun() 不能访问异步计算的结果。

四、异常处理

可以通过 handle() 方法来处理任务执行过程中可能出现的抛出异常的情况。

CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    if (true) {
        throw new RuntimeException("Computation error!");
    }
    return "hello!";
}).handle((res, ex) -> {
    // res 代表返回的结果
    // ex 的类型为 Throwable ,代表抛出的异常
    return res != null ? res : ex.getMessage();
});
System.out.println(future.get());

输出如下:

java.lang.RuntimeException: Computation error!

如果你想让 CompletableFuture 的结果就是异常的话,可以使用 completeExceptionally() 方法为其赋值。

五、组合 CompletableFuture

你可以使用 thenCompose() 按顺序链接两个 CompletableFuture 对象。

CompletableFuture<String> future
        = CompletableFuture.supplyAsync(() -> "hello!")
        .thenCompose(s -> CompletableFuture.supplyAsync(() -> s + "world!"));
System.out.println(future.get());

输出如下:

hello!world!

在实际开发中,这个方法还是非常有用的。比如说,我们先要获取用户信息然后再用用户信息去做其他事情。

thenCompose() 方法类似的还有 thenCombine() 方法, thenCombine() 同样可以组合两个 CompletableFuture 对象。

thenCompose() 可以两个 CompletableFuture 对象,并将前一个任务的返回结果作为下一个任务的参数,它们之间存在着先后顺序。

thenCombine() 会在两个任务都执行完成后,把两个任务的结果合并。两个任务是并行执行的,它们之间并没有先后依赖顺序。

CompletableFuture<String> completableFuture
        = CompletableFuture.supplyAsync(() -> "hello!")
        // 两个任务并行执行,执行完,进行合并操作
        .thenCombine(CompletableFuture.supplyAsync(
                () -> "world!"), (s1, s2) -> s1 + s2)
        .thenCompose(s -> CompletableFuture.supplyAsync(() -> s + "nice!"));
System.out.println(completableFuture.get());

输出如下:

hello!world!nice!

六、并行运行多个 CompletableFuture

你可以通过 CompletableFutureallOf()这个静态方法来并行运行多个 CompletableFuture

实际项目中,我们经常需要并行运行多个互不相关的任务,这些任务之间没有依赖关系,可以互相独立地运行。

比说我们要读取处理 6 个文件,这 6 个任务都是没有执行顺序依赖的任务,但是我们需要返回给用户的时候将这几个文件的处理的结果进行统计整理。像这种情况我们就可以使用并行运行多个 CompletableFuture 来处理。

示例代码如下:

        CompletableFuture<Void> task1 =
                CompletableFuture.supplyAsync(()->{
                    //自定义业务操作
                });
......
        CompletableFuture<Void> task6 =
                CompletableFuture.supplyAsync(()->{
                    //自定义业务操作
                });
......
        CompletableFuture<Void> headerFuture=CompletableFuture.allOf(task1,.....,task6);
        try {
            headerFuture.join();
        } catch (Exception ex) {
    ......
        }
        System.out.println("all done. ");
        ------

经常和 allOf() 方法拿来对比的是 anyOf() 方法。

allOf() 方法会等到所有的 CompletableFuture 都运行完成之后再返回 anyOf() 方法不会等待所有的 CompletableFuture 都运行完成之后再返回,只要有一个执行完成即可!

七、案例

模拟:平台商城,查询商品价格

class PlatShopping {
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    // 平台名称
    private String name;
    public PlatShopping(String name) {
        this.name = name;
    }
    /**
     * 获取书籍名称
     * @param bookName 书名
     * @return
     */
    public Double getPrice(String bookName) {
        try {
            // 模拟查询
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return Math.random() * 100;
    }

1、从多个平台获取书价格

构造多个平台查询价格

public static void main(String[] args) throws
        InterruptedException,
        ExecutionException {
    PlatShopping jd = new PlatShopping("京东");
    PlatShopping taobao = new PlatShopping("淘宝");
    PlatShopping tianmao= new PlatShopping("天猫");
    List<PlatShopping> platShoppings = new ArrayList<>();
    platShoppings.add(jd);
    platShoppings.add(taobao);
    platShoppings.add(tianmao);
    long c1 = currentTimeMillis();
    String allPlatPrice = getAllPlatPrice(platShoppings,"java高级编程");
    System.out.println(String.format("总耗时:%d", currentTimeMillis()- c1));
    System.out.println(allPlatPrice);
}

获取所有的书价格结果(顺序执行)

private static String getAllPlatPrice(List<PlatShopping> platShoppings, String bookName) {
    return platShoppings.stream().map(p->{
        Double price = p.getPrice(bookName);
        String data = format("%s 上 %s 的价格 %.2f", p.getName(), bookName, price);
        return   data;
    }).collect(Collectors.joining("\n"));
}

输出结果如下: 效率低

总耗时:3077
京东 上 java高级编程 的价格 60.47
淘宝 上 java高级编程 的价格 89.12
天猫 上 java高级编程 的价格 79.15

使用并行,硬编码处理。

    private static String getAllPlatPrice(List<PlatShopping> platShoppings, String bookName) {
        CompletableFuture<String> task1 = CompletableFuture.supplyAsync(() -> {
            PlatShopping p = platShoppings.get(0);
            Double price = p.getPrice(bookName);
            String data = format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
            return data;
        });
        CompletableFuture<String> task2 = CompletableFuture.supplyAsync(() -> {
            PlatShopping p = platShoppings.get(1);
            Double price = p.getPrice(bookName);
            String data = format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
            return data;
        });
        CompletableFuture<String> task3 = CompletableFuture.supplyAsync(() -> {
            PlatShopping p = platShoppings.get(2);
            Double price = p.getPrice(bookName);
            String data = format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
            return data;
        });
       return  task1.thenCombineAsync(task2,(s1,s2)->{
           return s1 + s2;
       }).thenCombineAsync(task3,(s1,s2) -> {
           return s1 + s2;
       }).join();
    }
}

输出结果如下:

总耗时:1065
京东 上 java高级编程 的价格 65.41 
淘宝 上 java高级编程 的价格 35.13 
天猫 上 java高级编程 的价格 19.70

使用allOf

private static String getAllPlatPrice(List<PlatShopping> platShoppings, String bookName) {
    CompletableFuture<String> task1 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(0);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    CompletableFuture<String> task2 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(1);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    CompletableFuture<String> task3 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(2);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    StringBuilder stringBuilder = new StringBuilder();
    // 等待三个都执行完成
    CompletableFuture.allOf(task1, task2, task3).join();
    // 获取结果
    stringBuilder.append(task1.join()).append(task2.join()).append(task3.join());
    return stringBuilder.toString();
}

输出结果如下:

总耗时:1064
京东 上 java高级编程 的价格 46.49 
淘宝 上 java高级编程 的价格 4.59 
天猫 上 java高级编程 的价格 74.47

使用流

private static String getAllPlatPrice(List<PlatShopping> platShoppings, String bookName) {
    // 批量提交任务,返回并行任务的集合列表
    List<CompletableFuture<String>> completableFutureList = platShoppings.stream().map(p -> {
        CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(() -> {
            String data = String.format("%s 上 %s 的价格 %.2f", p.getName(), bookName, p.getPrice(bookName));
            return data;
        });
        return completableFuture;
    }).collect(Collectors.toList());
    // 分别获取每个任务的结果,再进行聚合
    String result = completableFutureList.stream().map(c -> c.join())
            .collect(Collectors.joining("\n"));
    return result;
}

运行结果如下:

总耗时:1062
京东 上 java高级编程 的价格 69.99
淘宝 上 java高级编程 的价格 58.18
天猫 上 java高级编程 的价格 5.05

2、从任意一个平台获取结果就返回

构造多平台,

public static void main(String[] args) throws
        InterruptedException,
        ExecutionException {
    PlatShopping jd = new PlatShopping("京东");
    PlatShopping taobao = new PlatShopping("淘宝");
    PlatShopping tianmao= new PlatShopping("天猫");
    List<PlatShopping> platShoppings = new ArrayList<>();
    platShoppings.add(jd);
    platShoppings.add(taobao);
    platShoppings.add(tianmao);
    long c1 = currentTimeMillis();
    String onePrice = getOnePrice(platShoppings,"java高级编程");
    System.out.println(String.format("总耗时:%d", currentTimeMillis()- c1));
    System.out.println(onePrice);
}

使用anyOf

private static String getOnePrice(List<PlatShopping> platShoppings, String bookName) {
    CompletableFuture<String> task1 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(0);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    CompletableFuture<String> task2 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(1);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    CompletableFuture<String> task3 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(2);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    Object join = CompletableFuture.anyOf(task1, task2, task3).join();
    return (String) join;
}

输出如下:

总耗时:1063
京东 上 java高级编程 的价格 4.93

使用 applyToEitherAsync

private static String getOnePrice(List<PlatShopping> platShoppings, String bookName) {
    CompletableFuture<String> task1 = CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(0);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    });
    String result = task1.applyToEitherAsync(CompletableFuture.supplyAsync(() -> {
        PlatShopping p = platShoppings.get(1);
        Double price = p.getPrice(bookName);
        String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
        return data;
    }), (t) -> t).applyToEitherAsync(
            CompletableFuture.supplyAsync(() -> {
                PlatShopping p = platShoppings.get(2);
                Double price = p.getPrice(bookName);
                String data = String.format("%s 上 %s 的价格 %.2f \n", p.getName(), bookName, price);
                return data;
            }),
            (t) -> t
    ).join();
    return result;
}

输出如下:

总耗时:1063
京东 上 java高级编程 的价格 52.31

另外,建议可以看看京东的 asyncToolopen in new window 这个并发框架,里面大量使用到了 CompletableFuture 。

以上就是java异步编程CompletableFuture使用示例详解的详细内容,更多关于java异步CompletableFuture的资料请关注我们其它相关文章!

(0)

相关推荐

  • java异步编程之一文看完其异步函数表

    目录 1 低层级 asyncio 索引 1.1 获取事件循环 1.2 事件循环方法集 1.3 传输 1.3.1 读取传输 1.3.2 写入传输 1.3.3 数据报传输 1.3.4 子进程传输 1.3.5 协议 1.3.6 流协议 (TCP, Unix 套接字, 管道) 1.3.7 缓冲流协议 1.3.8 数据报协议 1.3.9 子进程协议 事件循环策略 2 高层 API索引 2.1 任务 例子 2 队列集 2.1 子进程集 3 同步 小结 1 低层级 asyncio 索引 低层级 API 索引¶

  • Java CompletableFuture实现多线程异步编排

    目录 一 :问题背景 二 :CompletableFuture介绍 三 :具体场景 1.0 单个任务 1.0.1 runAsync:无返回值 1.0.2 supplyAsync:有返回值 1.0.3 supplyAsync:有返回值 2.0 两个任务编排 2.0.1 thenRunAsync 2.0.2 thenAcceptAsync 2.0.3 thenApplyAsync 3.0 三任务编排 3.0.1 三任务组合 3.0.2 三任务组合二 4.0 多任务的编排 4.0.1.allOf:所有

  • java开发线上事故理解RocketMQ异步精髓

    目录 引言 1 业务场景 2 线程池模式 3 本地内存 + 定时任务 4 MQ 模式 5 Agent 服务 + MQ 模式 6 总结 第一层:什么场景下需要异步 第二层:异步的外功心法 第三层:异步的本质 引言 在高并发的场景下,异步是一个极其重要的优化方向. 前段时间,生产环境发生一次事故,笔者认为事故的场景非常具备典型性 . 写这篇文章,笔者想和大家深入探讨该场景的架构优化方案.希望大家读完之后,可以对异步有更深刻的理解. 1 业务场景 老师登录教研平台,会看到课程列表,点击课程后,课程会以

  • java CompletableFuture异步任务编排示例详解

    目录 前言 同步串行 异步串行 并行任务 多任务结果合并计算 任一任务完成 快速失败 注意 前言 在之前的项目开发中,都没怎么使用过CompletableFuture的功能,只听说过和异步编程有关.为了能够在将来有需要的时候用得上,这两天花了点时间学习了一下,并简单地总结一下如何使用CompletableFuture完成异步任务编排. 先创建一个自定义的线程池,后续所有代码都会使用到: private static final ThreadPoolExecutor THREAD_POOL_EXE

  • java异步编程CompletableFuture使用示例详解

    目录 一.简单介绍 二.常见操作 1.使用默认线程池 2.使用自定义线程池 3.获取线程的执行结果 三.处理异步结算的结果 四.异常处理 五.组合 CompletableFuture 六.并行运行多个 CompletableFuture 七.案例 1.从多个平台获取书价格 2.从任意一个平台获取结果就返回 一.简单介绍 CompletableFuture 同时实现了 Future 和 CompletionStage 接口. public class CompletableFuture<T> i

  • Java异步编程工具Twitter Future详解

    目录 异步编程(Twitter Future) 为啥要异步 基本用法 1.封装计算逻辑,异步返回. 2.异步计算结果串联异步处理 3.并行多个异步任务,统一等待结果 4.异步错误处理 Twitter包装 pom依赖 1.封装计算逻辑,异步返回 2.异步计算结果串联异步处理 3.并行多个异步任务 4.错误处理 其他用法 其他工具 异步编程(Twitter Future) 为啥要异步 异步编程有点难以理解,这东西感觉不符合常理,因为我们思考都是按照串行的逻辑,事都是一件一件办.但在异步计算的情况下,

  • Java并发编程Semaphore计数信号量详解

    Semaphore 是一个计数信号量,它的本质是一个共享锁.信号量维护了一个信号量许可集.线程可以通过调用acquire()来获取信号量的许可:当信号量中有可用的许可时,线程能获取该许可:否则线程必须等待,直到有可用的许可为止. 线程可以通过release()来释放它所持有的信号量许可(用完信号量之后必须释放,不然其他线程可能会无法获取信号量). 简单示例: package me.socketthread; import java.util.concurrent.ExecutorService;

  • Java并发编程预防死锁过程详解

    这篇文章主要介绍了Java并发编程预防死锁过程详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 在java并发编程领域已经有技术大咖总结出了发生死锁的条件,只有四个条件都发生时才会出现死锁: 1.互斥,共享资源X和Y只能被一个线程占用 2.占有且等待,线程T1已经取得共享资源X,在等待共享资源Y的时候,不释放共享资源X 3.不可抢占,其他线程不能强行抢占线程T1占有的资源 4.循环等待,线程T1等待线程T2占有的资源,线程T2等待线程T1占有

  • C#异步编程async/await用法详解

    异步函数简介 一般指 async 修饰符声明得.可包含await表达式得方法或匿名函数. 声明方式 异步方法的声明语法与其他方法完全一样, 只是需要包含 async 关键字.async可以出现在返回值之前的任何位置, 如下示例: async public static void GetInfoAsync() { //... } public async static void GetInfoAsync() { //... } public static async void GetInfoAsy

  • Java设计模式之策略模式示例详解

    目录 定义 结构 UML类图 UML序列图 深入理解策略模式 策略和上下文的关系 策略模式在JDK中的应用 该策略接口有四个实现类 策略模式的优点 策略模式的缺点 策略模式的本质 在讲策略模式之前,我们先看一个日常生活中的小例子: 现实生活中我们到商场买东西的时候,卖场往往根据不同的客户制定不同的报价策略,比如针对新客户不打折扣,针对老客户打9折,针对VIP客户打8折... 现在我们要做一个报价管理的模块,简要点就是要针对不同的客户,提供不同的折扣报价. 如果是有你来做,你会怎么做? 我们很有可

  • Java I/O流使用示例详解

    目录 1.java IO包 2.创建文件 3.获取文件信息 4.目录操作 5.字节输入流InputStream 6.字节输出流FileOutputStream 7.模拟文件拷贝 8.字符输入流FileReader 9.字符输出流FileWriter 1.java IO包 Java.io 包几乎包含了所有操作输入.输出需要的类.所有这些流类代表了输入源和输出目标. Java.io 包中的流支持很多种格式,比如:基本类型.对象.本地化字符集等等. 一个流可以理解为一个数据的序列.输入流表示从一个源读

  • Kotlin编程条件控制示例详解

    目录 本文总览 1. When 表达式 2. If 表达式 总结 本文总览 本篇来看看 Kotlin的条件控制,这一节知识点 建议与Java中的条件结构类比,会很好理解并记住. 1. When 表达式 在 Kotlin 用 when 来定义多个分支的条件表达式.Kotlin中这个语法与 java 中的 switch 语句非常类似.代码块的执行就是将参数与所有的分⽀条件顺序⽐较,直到满⾜某个分⽀条件:(示例 ) when (x) { 1 -> print("x == 1") 2 -

  • Kotlin编程基础数据类型示例详解

    目录 本文总览 1.数值类型 2.布尔型 3.字符串 3.1 字符串字面值 3.2 字符串模板 4.数组 4.1 普通数组 4.2 原⽣类型数组 5.类型检测和类型转换 5.1 智能转换 5.2 is 与 !is 操作符 5.3 转换操作符: as 与 as? 总结 本文总览 上一篇学习了Kotlin基础语法知识,本篇开始会深入探讨一下Kotlin各个基础语法点.首先来熟悉Kotlin的数据类型和类型转换版块. 1.数值类型 在Kotlin中提供了数值类型: 整数类型:Byte,Short,In

  • Java并发编程总结——慎用CAS详解

    一.CAS和synchronized适用场景 1.对于资源竞争较少的情况,使用synchronized同步锁进行线程阻塞和唤醒切换以及用户态内核态间的切换操作额外浪费消耗cpu资源:而CAS基于硬件实现,不需要进入内核,不需要切换线程,操作自旋几率较少,因此可以获得更高的性能. 2.对于资源竞争严重的情况,CAS自旋的概率会比较大,从而浪费更多的CPU资源,效率低于synchronized.以java.util.concurrent.atomic包中AtomicInteger类为例,其getAn

随机推荐