美文网首页js css html
线程池优化for循环

线程池优化for循环

作者: Raral | 来源:发表于2022-10-25 11:47 被阅读0次

线程池优化for循环

列子


import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.*;
import java.util.stream.Collectors;

/**
 * 循环里面使用线程池执行里面东西
 */
public class Test1 {

    public static ThreadPoolExecutor threadPoolExecutor;

    public static List<String> list1;

    public static void main(String[] args) {

        //创建线程池 普通的
        threadPoolExecutor = new ThreadPoolExecutor(128, 128, 0, TimeUnit.MILLISECONDS,
                new LinkedBlockingQueue<>(Integer.MAX_VALUE));

        List<String> list = new ArrayList<>();
        list.add("0");
        list.add("1");
        list.add("2");
        list.add("3");
        list.add("4");
        list.add("5");
        list.add("6");
        list.add("7");
        list.add("8");
        list.add("9");
        long l = System.currentTimeMillis();
        m1(list);
        long l1 = System.currentTimeMillis();
        System.out.println("耗时:" + (l1- l) + "ms");
        System.out.println(list1);
    }

    //没使用线程池处理
    public static void m1(List<String> list) {
        List<String> objects = new ArrayList<>();
        list.stream().forEach(item -> {
            try {
                new Thread().sleep(1000);//模拟执行延迟
                System.out.println("[0]" + Thread.currentThread().getName()+"----"+item);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }
            objects.add(item + "A");//stream内部访问不了list1
            System.out.println(objects);
        });
        list1 = objects;
        System.out.println("stream");
    }

    //线程没有顺序执行的,时间短
    public static void m2(List<String> list) {
        for (String s : list) {
//            System.out.println(s);
            Runnable run = new Runnable() {
                public void run() {
                    try {
                        new Thread().sleep(1000);
                        //模拟耗时操作
                        System.out.println("[1]" + Thread.currentThread().getName()+"----"+s);
                        list1.add(s + "A");
                    } catch (Exception e) {
                    }
                }
            };
            threadPoolExecutor.execute(run);
        }

    }

    public static void m3(List<String> list) {
         List<String> objects = new ArrayList<>();
        list.stream().map(item -> {

            return threadPoolExecutor.submit(() -> {
                try {
                    new Thread().sleep(1000);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
                System.out.println("[1]" + Thread.currentThread().getName()+"----"+item);
                synchronized (objects) {
                    objects.add(item + "A");
                }
            });
        }).forEach(future -> wait4Done(future));
        list1 = objects;

    }


    //等待执行完成,第一个线程执行完后,才会执行下一个线程任务
    public static void wait4Done(Future future) {
        try {
            if (future != null) {
                future.get();
            }
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        } catch (ExecutionException e) {
            throw new RuntimeException(e);
        }
    }


}

效果

  1. m1方法:正常循环执行
[0]main----0
[0A]
[0]main----1
[0A, 1A]
[0]main----2
[0A, 1A, 2A]
[0]main----3
[0A, 1A, 2A, 3A]
[0]main----4
[0A, 1A, 2A, 3A, 4A]
[0]main----5
[0A, 1A, 2A, 3A, 4A, 5A]
[0]main----6
[0A, 1A, 2A, 3A, 4A, 5A, 6A]
[0]main----7
[0A, 1A, 2A, 3A, 4A, 5A, 6A, 7A]
[0]main----8
[0A, 1A, 2A, 3A, 4A, 5A, 6A, 7A, 8A]
[0]main----9
[0A, 1A, 2A, 3A, 4A, 5A, 6A, 7A, 8A, 9A]
stream
耗时:10188ms
[0A, 1A, 2A, 3A, 4A, 5A, 6A, 7A, 8A, 9A]
  1. m2方法: 使用线程池执行里循环内容
耗时:4ms
list1:null
[1]pool-1-thread-7----6
[1]pool-1-thread-4----3
[1]pool-1-thread-2----1
[1]pool-1-thread-9----8
[1]pool-1-thread-6----5
[1]pool-1-thread-3----2
[1]pool-1-thread-1----0
[1]pool-1-thread-8----7
[1]pool-1-thread-10----9
[1]pool-1-thread-5----4
  1. m3方法:如果不加wait4Done效果个m2一样
[1]pool-1-thread-1----0
[1]pool-1-thread-2----1
[1]pool-1-thread-3----2
[1]pool-1-thread-4----3
[1]pool-1-thread-5----4
[1]pool-1-thread-6----5
[1]pool-1-thread-7----6
[1]pool-1-thread-8----7
[1]pool-1-thread-9----8
[1]pool-1-thread-10----9
耗时:10183ms
list1:[0A, 1A, 2A, 3A, 4A, 5A, 6A, 7A, 8A, 9A]

注意

  1. 使用java stream时,内部不可以访问外部静态变量
  2. 用stream().parallel().forEach(),这个parallel是可以让循环并行的,提高了程序的效率。但是在我使用它往一个list中设置值的时候,发现了问题。由于是多线程异步运行,所以循环可能并不保证全部运行完才进行下一步,所以如果在循环之后对list有其他操作,可能这个list并不完整,这样得到的数据就会有问题。
    所以正确的做法是,如果循环后面没有操作,只是需要在循环体内进行操作的话,用parallel可以提高效率。但是如果循环后面要对循环里面设置的值做操作,就不能使用parallel了。

相关文章

  • 线程池优化for循环

    线程池优化for循环 列子 效果 m1方法:正常循环执行 m2方法: 使用线程池执行里循环内容 m3方法:如果不加...

  • Android性能优化(五)线程优化及优化建议

    线程优化 线程优化的思想是采用线程池,避免程序中存在大量的Thread,线程池可以重用内部的线程,从而避免了线程的...

  • 线程池与Threadlocal

    线程池与Threadlocal 线程池: 线程池是为了使线程能够得到循环的利用,线程池里面养着一些线程,有任务需要...

  • Java线程池-手写简易线程池

    什么是线程池 线程池就是以一个或多个线程[循环执行]多个应用逻辑的线程集合. 线程池的作用: 线程池作用就是限制系...

  • 线程池的原理

    参考 深入Java源码理解线程池原理 线程池是对CPU利用的优化手段 线程池使用池化技术实现,替他的实现还有连接池...

  • Java 线程池

    线程池是什么? 线程池用于多线程处理中,它可以根据系统的情况,可以有效控制线程执行的数量,优化运行效果。线程池做的...

  • ThreadPoolExecutor实战(一:线程池参数)

    线程池是什么? 线程池是多线程开发中关键技术之一,线程池能够提高系统性能,是为了优化直接创建线程产生的问题而存在的...

  • 聊聊Java线程池那些事

    为什么使用线程池 线程池作用就是通过限制系统中执行线程的数量从而达到优化资源分配的目的。 控制执行线程的数量 假如...

  • Tomcat优化思路

    1 优化思路梳理 2 线程池优化 3 Tomcat 内存优化 4 Tomcat 的其他优化 5 Tomcat三种线...

  • Android 线程池

    1.含义 线程池用于多线程处理中,它可以根据系统的情况,可以有效控制线程执行的数量,优化运行效果。线程池做的工作主...

网友评论

    本文标题:线程池优化for循环

    本文链接:https://www.haomeiwen.com/subject/fbwnzrtx.html