java

java并发-多线程一定快吗

1.1上下文切换

1.1.1多线程一定快吗

示例:

package top.deng.concurrencytest;

/**
 * @Desc 多线程一定快吗?
 * @since 2020/5/12 上午11:06
 */
public class ConcurrencyTest {
    private static final long count = 1000000000L; // 值较大时,并行执行比串行更快;较小时串行更快,因为线程有创建和上下文切换的开销

    public static void main(String[] args) throws InterruptedException {
        concurrency();
        serial();
    }

    /**
     * 并发执行
     * @throws InterruptedException
     */
    private static void concurrency() throws InterruptedException {
        long start = System.currentTimeMillis();
        Thread  t = new Thread(()->{
            int a = 0;
            for(long i = 0; i < count; i++){
                a += 5;
            }
        });
        t.start();
        int b = 0;
        for(long i = 0; i < count; i++){
            b--;
        }
        t.join();
        long time = System.currentTimeMillis() - start;
        System.out.println("currency:" + time +"ms, b = " + b);
    }

    /**
     * 串行执行
     */
    private static void serial(){
        long start = System.currentTimeMillis();

        int a = 0;
        for(long i = 0; i < count; i++){
            a += 5;
        }
        int b = 0;
        for(long i = 0; i < count; i++){
            b--;
        }
        long time = System.currentTimeMillis() - start;
        System.out.println("serial:" + time +"ms, b = " + b + ",a = " + a);
    }
}

1.1.2 测试上下文切换次数和时长

  • 使用vmstat可以测量上下文切换的次数。

1.1.3 如何减少上下文切换

  • 无锁并发编程,不同的线程处理不同的数据。
  • CAS算法
  • 使用最少线程,避免创建不需要的线程

1.1.4 减少线程上下文切换实战

查看java进程的线程状态

jstack [pid] > dump.txt

统计线程状态数量

grep java.lang.Thread.State dump.txt | awk '{print $2$3$4$5}' | sort |uniq -c

关于作者

程序员,软件工程师,java, golang, rust, c, python,vue, Springboot, mybatis, mysql,elasticsearch, docker, maven, gcc, linux, ubuntu, centos, axum,llm, paddlepaddle, onlyoffice,minio,银河麒麟,中科方德,rpm