【问题标题】:Running code when all threads are finished processing当所有线程完成处理时运行代码
【发布时间】:2011-01-04 06:56:23
【问题描述】:

快速说明:Java 和 Android 菜鸟在这里,我愿意告诉你我很愚蠢(只要你告诉我为什么。)

我有一个 android 应用程序,它要求我启动来自不同类的多个线程,并且只有在所有线程都完成工作后才能进入下一个活动。我还想添加一个“故障安全”超时,以防线程花费太长时间(HTTP 请求花费太长时间或其他原因。)

我搜索了 Stack Overflow,发现一个帖子说我应该创建一个类来保持打开的线程总数,然后使用计时器来轮询所有线程何时完成。

我想我已经创建了一个工作类来为我做这件事,它尚未经过测试,但在 eclipse 中没有显示任何错误。

这是一个正确的实现吗?是否有任何 API 需要我注意(例如 Java 或 Android API 中的类,可以用来代替类底部的抽象类?)

package com.dmp.geofix.libs;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.Timer;
import java.util.TimerTask;

public class ThreadMonitor {

    private Timer timer = null;
    private TimerTask timerTask = null;
    private OnSuccess onSuccess = null;
    private OnError onError = null;

    private static ArrayList<Thread> threads;

    private final int POLL_OPEN_THREADS = 100;
    private final int TIMEOUT = 10000;

    public ThreadMonitor() {
        timerTask = new PollThreadsTask();
    }

    public ThreadMonitor(OnSuccess s) {
        timerTask = new PollThreadsTask();
        onSuccess = s;
    }

    public ThreadMonitor(OnError e) {
        timerTask = new PollThreadsTask();
        onError = e;
    }

    public ThreadMonitor(OnSuccess s, OnError e) {
        timerTask = new PollThreadsTask();
        onSuccess = s;
        onError = e;
    }

    public void start() {
        Iterator<Thread> i = threads.iterator();
        while (i.hasNext()) {
            i.next().start();
        }

        timer = new Timer();
        timer.schedule(timerTask, 0, POLL_OPEN_THREADS);
    }

    public void finish() {
        Iterator<Thread> i = threads.iterator();
        while (i.hasNext()) {
            i.next().interrupt();
        }

        threads.clear();
        timer.cancel();
    }

    public void addThread(Thread t) {
        threads.add(t);
    }

    public void removeThread(Thread t) {
        threads.remove(t);
        t.interrupt();
    }

    class PollThreadsTask extends TimerTask {

        private int timeElapsed = 0;

        @Override
        public void run() {
            timeElapsed += POLL_OPEN_THREADS;
            if (timeElapsed <= TIMEOUT) {
                if (threads.isEmpty() == false) {
                    if (onSuccess != null) {
                        onSuccess.run();
                    }
                }
            } else {
                if (onError != null) {
                    onError.run();
                }
                finish();
            }
        }

    }

    public abstract class OnSuccess {
        public abstract void run();
    }

    public abstract class OnError {
        public abstract void run();
    }

}

【问题讨论】:

    标签: java android multithreading timer


    【解决方案1】:

    看看Thread.join

    【讨论】:

      【解决方案2】:

      检查 java.util.concurrent 包。 特别是 Future、FutureTask 和 ExecutorService FutureTask 允许使用方法 isDone() 获取正在执行的操作的状态

      希望对你有帮助

      【讨论】:

        【解决方案3】:

        所有线程都应该实现可调用,它们应该是未来的任务。

        使用 countdownlatch/CyclicBarrier 启动它们,以确保它们同时启动

        【讨论】:

        • 不会在所有线程上实现 callable 并将它们传递给 FutureTask 使它们多次调用该代码吗?我只想等待一切完成,然后调用一个方法,一次,使用备用代码块(如果一个线程超时)。
        • 只有在完成处理的某些线程必须等待剩余线程时才能使用Join。如何检查其他线程的超时情况。
        • 只有在完成处理的某些线程必须等待剩余线程时才能使用Join。你怎么能检查其他线程的超时事情。再添加一个线程作为监控线程来检查线程是否仍在处理中。取消那些超时的任务。添加倒计时锁存器保证所有任务同时启动
        【解决方案4】:

        如果您希望应用程序在运行代码后退出,您可能需要查看 Runtime.getRuntime().addShutdownHook(Thread) 来指定应用程序退出时要执行的线程。

        【讨论】:

        • 这是在一个 android 应用程序中,因此当应用程序退出时会有一个“正确的”android 运行代码的方式。 Activity 类中的 onPause() 和 onStop() 回调方法。
        猜你喜欢
        • 1970-01-01
        • 2013-10-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-01-10
        • 1970-01-01
        • 2011-12-07
        相关资源
        最近更新 更多