前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >主线程都结束了,为何进程还在执行

主线程都结束了,为何进程还在执行

作者头像
FunTester
发布2019-09-17 15:33:18
9370
发布2019-09-17 15:33:18
举报
文章被收录于专栏:FunTesterFunTester

本人在做APP性能测试的过程中,曾经遇到过一个比较尴尬的问题,主线程已经结束,但是程序依然在执行,但没有找到在执行什么,一时非常苦恼。先分享一下自己的代码,再说我找到的原因。

代码语言:javascript
复制
public static void main(String[] args) {
        String timess = args[0];
        int times = Common.getInstance().changeStringToInt(timess);
        for (int i = 0; i < times; i++) {
            Date start = Common.getInstance().getDate();
            StartApp startApp = new StartApp();// 新建启动app线程
            Logcat logcat = new Logcat();// 新建记录log线程
            PerformanceThread performanceThread = new PerformanceThread("monkey", package_name);// 性能监控
            performanceThread.start();
            startApp.start();
            logcat.start();
            execCmdAdb(command, "monkey" + getNow() + ".log");
            startApp.stopThread();
            logcat.stopLoacat();
            performanceThread.stopRecord();
            Date end = Common.getInstance().getDate();
            Common.getInstance().outputTimeDiffer(start, end, "第" + i + "次");
        }
        output("结束monkey了!");
    }

就是新启了几个线程,我猜测应该是这些线程没有很好的结束掉,导致后面出现很多问题。经过检查发现在启动APP的线程里面。这个线程做的事情就是每分钟启动一次APP,并检查一下WiFi状态,使WiFi保持开/关,十分钟反转一下WiFi的状态。主线程结束后,这些进程还在sleep()休眠状态,所以才会没找到执行的代码。分享一下这个类有问题的代码:

代码语言:javascript
复制
@Override
    public void run() {
        while (MKEY) {
            int num = Common.getInstance().getRandomInt(4);
            if (num == 1) {
                stopJuziApp();
                Common.getInstance().sleep(500);
            }
            Common.getInstance().sleep(60 * 1000);
            keepWifiONorOFF(WIFISTATUS);
            startJuziApp();
        }
    }
代码语言:javascript
复制
public void run() {
        while (WIFIKEY) {
            for (int i = 0; i < 10; i++) {
                if (WIFIKEY) {
                    break;
                }
                Common.getInstance().sleep(60 * 1000);
                keepWifiONorOFF(WIFISTATUS);
            }
            WIFISTATUS = !WIFISTATUS;// 反转WiFi状态
        }
    }

就是因为这里面的sleep()导致了之前的原因,后来我把WiFiswitch的代码改掉了,放在startAPP里面方法里面了。然后在用java多线程里面的join方法在每个线程加入到主线程,这样就可以避免主线程结束而其他线程还在运行的尴尬了。分享改之后的代码:

代码语言:javascript
复制
public static void main(String[] args) throws InterruptedException {
        String timess = args[0];
        int times = Common.getInstance().changeStringToInt(timess);
        for (int i = 0; i < times; i++) {
            Date start = Common.getInstance().getDate();
            StartApp startApp = new StartApp();// 新建启动app线程
            Logcat logcat = new Logcat();// 新建记录log线程
            PerformanceThread performanceThread = new PerformanceThread("monkey", package_name);// 性能监控
            performanceThread.start();
            startApp.start();
            logcat.start();
            execCmdAdb(command, "monkey" + getNow() + ".log");
            startApp.stopThread();
            logcat.stopLoacat();
            performanceThread.stopRecord();
            logcat.join();
            performanceThread.join();
            startApp.join();
            Date end = Common.getInstance().getDate();
            Common.getInstance().outputTimeDiffer(start, end, "第" + i + "次");
        }
        output("结束monkey了!");
    }

或者可以封装一个方法来完成:

代码语言:javascript
复制
    public static void main(String[] args) throws InterruptedException {
        String timess = args[0];
        int times = Common.getInstance().changeStringToInt(timess);
        for (int i = 0; i < times; i++) {
            Date start = Common.getInstance().getDate();
            StartApp startApp = new StartApp();// 新建启动app线程
            Logcat logcat = new Logcat();// 新建记录log线程
            PerformanceThread performanceThread = new PerformanceThread("monkey", package_name);// 性能监控
            performanceThread.start();
            startApp.start();
            logcat.start();
            execCmdAdb(command, "monkey" + getNow() + ".log");
            startApp.stopThread();
            logcat.stopLoacat();
            performanceThread.stopRecord();
            joinThread(logcat, startApp, performanceThread);
            Date end = Common.getInstance().getDate();
            Common.getInstance().outputTimeDiffer(start, end, "第" + i + "次");
        }
        output("结束monkey了!");
    }

    /**
     * 把所有线程加入到主线程里面
     * 
     * @param threads
     */
    public static void joinThread(Thread... threads) {
        for (Thread thread : threads) {
            try {
                thread.join();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

技术类文章精选

  1. java一行代码打印心形
  2. Linux性能监控软件netdata中文汉化版
  3. 接口测试代码覆盖率(jacoco)方案分享
  4. 性能测试框架
  5. 如何在Linux命令行界面愉快进行性能测试
  6. 图解HTTP脑图
  7. 如何测试概率型业务接口
  8. httpclient处理多用户同时在线
  9. 将swagger文档自动变成测试代码
  10. 五行代码构建静态博客
  11. httpclient如何处理302重定向
  12. 基于java的直线型接口测试框架初探
  13. Tcloud 云测平台--集大成者

非技术文章精选

  1. 为什么选择软件测试作为职业道路?
  2. 成为杰出Java开发人员的10个步骤
  3. 写给所有人的编程思维
  4. 自动化测试的障碍
  5. 自动化测试的问题所在
  6. 测试之《代码不朽》脑图
  7. 成为优秀自动化测试工程师的7个步骤
本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2019-09-14,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 FunTester 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 技术类文章精选
  • 非技术文章精选
相关产品与服务
应用性能监控
应用性能监控(Application Performance Management,APM)是一款应用性能管理平台,基于实时多语言应用探针全量采集技术,为您提供分布式性能分析和故障自检能力。APM 协助您在复杂的业务系统里快速定位性能问题,降低 MTTR(平均故障恢复时间),实时了解并追踪应用性能,提升用户体验。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档