Android 线程优化插件使用(第一篇)

前言

本插件内容是结合多家博客的精华改造而成的

插件地址:github.com/heyan224/la...

该插件主要是基于github.com/Knight-ZXW/... 的基础上细化改造的

目标

线程优化就是将自己代码中的线程以及各种sdk 中创建的线程都收敛到统一的线程池中,方便线程的管理。

我们知道创建线程的方式有多种:

  • new Thread
  • new ScheduledThreadPoolExecutor
  • new ThreadPoolExecutor
  • new FixedThreadPool
  • new CachedThreadPool
  • Executors.newSingleThreadExecutor()
  • new HandlerThread

随着业务的膨胀以及接入各种三方sdk越来越多,那么在我们的apk中将存在大量无法管控的Thread实例以及 ThreadPoolExecutor 实例。

所以要达到线程收敛的目的就是要将 各种 new Thread 以及new ThreadPoolExecutor 等等实例都变成 一个 ,比如new ProxyThreadnew PThreadPoolExecutor

以某一个sdk为例,线程收敛前某sdk的现状如下:

优化后:

我们已经将sdk中new Thread 以及new ThreadPoolExecutor 相关代码都改了

问题来了,即使都改成了new ProxyThread new PThreadPoolExecutor,这不是依然有很多线程和线程池的实例吗,依然没有达到收敛的目的?

确实,要想达到收敛的目的,还需要做一些事情,拿PThreadPoolExecutor 为例

我们在PThreadPoolExecutor 重写了ThreadPoolExecutor中的 execute 方法和 submit方法,当有人向线程池中提交任务时,我们这里并没有开启线程,而是通过 DefaultThreadPoolExecutor.getHCoreThreadPool ().execute(command) 将任务丢到了新的线程池中。 所以可以看出PThreadPoolExecutor 并不是真正的线程池,真正的线程池是 getHCoreThreadPool(),它是一个单例。

kotlin 复制代码
public class PThreadPoolExecutor  extends ThreadPoolExecutor {
//..........
//.........

    @Override
    public void execute(Runnable command) {
        if (!SuperThreadPoolManager.isProxyThreadEnable()) {
            super.execute(command);
            return;
        }
        try {
            DefaultThreadPoolExecutor.getHCoreThreadPool().execute(command);
        } catch (OutOfMemoryError error) {
            DefaultThreadPoolExecutor.getExtraThreadPool().execute(command);
        }
    }


    @Override
    public Future<?> submit(Runnable task) {
        if (!SuperThreadPoolManager.isProxyThreadEnable()) {
            return super.submit(task);
        }

        try {
            return DefaultThreadPoolExecutor.getHCoreThreadPool().submit(task);
        } catch (OutOfMemoryError error) {
            return DefaultThreadPoolExecutor.getExtraThreadPool().submit(task);
        }
    }


    @Override
    public <T> Future<T> submit(Callable<T> task) {
        if (!SuperThreadPoolManager.isProxyThreadEnable()) {
            return super.submit(task);
        }
        try {
            return DefaultThreadPoolExecutor.getHCoreThreadPool().submit(task);
        } catch (OutOfMemoryError error) {
            return DefaultThreadPoolExecutor.getExtraThreadPool().submit(task);
        }

    }
}

使用

  • 项目的根目录下的build.gradle中添加

classpath 'io.github.heyan224:lancet-plugin:0.0.6'

  • app目录下的build.gradle中添加

implementation 'io.github.heyan224:lancet-runtime:0.0.2'

  • 还是在 app目录下的build.gradle中添加如下的配置
bash 复制代码
apply plugin: 'LancetX'
LancetX{
    enable true
    enableInDebug true

    weaveGroup {

        threadOptimize {
            enable false
            whiteNames = [
                    "com/bb",
                    "com/aa",
                    "com/xx"
            ]
            blackNames = [

            ]
        }

    }
}

这里解释几个关键的字段:

arduino 复制代码
threadOptimize { // 线程优化配置项
enable true  // 开关
    whiteNames = [   // 白名单,我们可以添加白名单,来指定特定的几个sdk来进行线程优化
            "com/bb",
            "com/aa",
            "com/xx"
    ]
    blackNames = [  // 黑名单

    ]
} 
  • 最后一步就是来实现 我们自己的ProxyThread PThreadPoolExecutor 代码了,以及 ThreadProxyThread的映射,ThreadPoolExecutorPThreadPoolExecutor的映射

也就是我们要告诉字节码修改插件,我们想要修改哪些类,比如我们将要修改 Thread 类,修改为 ProxyThread,代码如下图。

另外 ProxyThreadPThreadPoolExecutorgetHCoreThreadPool()的实现都已在仓库中了

注意点

线程收敛到这里其实还没开始,因为真正重要的是我们的代理线程池的参数应该如何配置。

我们都知道线程池有几个重要的参数需要深思熟虑

  • 线程池核心线程数
  • 线程池最大线程数
  • 任务等待队列
  • 线程空闲多久要回收,也就是keepAliveTime
  • 线程任务拒绝策略的制定 RejectedExecutionHandler

这几个参数的制定对于线程收敛很重要。

相关推荐
_.Switch2 小时前
Python机器学习:自然语言处理、计算机视觉与强化学习
python·机器学习·计算机视觉·自然语言处理·架构·tensorflow·scikit-learn
落落落sss2 小时前
MybatisPlus
android·java·开发语言·spring·tomcat·rabbitmq·mybatis
代码敲上天.3 小时前
数据库语句优化
android·数据库·adb
GEEKVIP5 小时前
手机使用技巧:8 个 Android 锁屏移除工具 [解锁 Android]
android·macos·ios·智能手机·电脑·手机·iphone
feng_xiaoshi6 小时前
【云原生】云原生架构的反模式
云原生·架构
model20057 小时前
android + tflite 分类APP开发-2
android·分类·tflite
彭于晏6897 小时前
Android广播
android·java·开发语言
架构师吕师傅8 小时前
性能优化实战(三):缓存为王-面向缓存的设计
后端·微服务·架构
与衫8 小时前
掌握嵌套子查询:复杂 SQL 中 * 列的准确表列关系
android·javascript·sql
团儿.10 小时前
解锁MySQL高可用新境界:深入探索MHA架构的无限魅力与实战部署
数据库·mysql·架构·mysql之mha架构