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

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

相关推荐
Kstheme19 小时前
把任何 GitHub 仓库变成系统设计课:这个开源项目做到了
架构
Kapaseker19 小时前
5 分钟搞懂 Kotlin DSL
android·kotlin
禅思院19 小时前
路由性能高可用架构实战方案
前端·架构·前端框架
恋猫de小郭20 小时前
AI Agent 开发究竟是啥?如何用 AI 开发 Agent ?深入浅出给你一套概念
android·前端·ai编程
黄林晴20 小时前
Android 17 正式发布!target 37 一大批旧代码直接不能用了
android
Carson带你学Android20 小时前
Android 17 正式发布:AI 终于成了系统能力
android·前端·ai编程
三少爷的鞋20 小时前
当 UseCase 开始长期监听,它可能已经不是 UseCase 了
android
恋猫de小郭1 天前
Android 限制侧载新进展,谷歌联合国内厂商推验证计划
android·前端·flutter
恋猫de小郭1 天前
解读 Android 17 全新内存限制,有没有“豁免”后门?
android·前端·flutter
贾艺驰2 天前
实战Android Framework: 新增一个系统权限
android