如何强制停止线程并使用新变量启动相同的线程?

时间:2017-02-03 03:28:09

标签: android multithreading task

如果用户再次单击该按钮,当前任务强制停止并将执行下一个任务,我想在按钮单击时执行一些长时间运行的任务?

4 个答案:

答案 0 :(得分:0)

  

一旦线程停止,就无法重启线程。

我建议使用Looper/Handler API将任务放入队列中,让处理程序在不同的线程上执行它们。

我有looper / handler here的演示项目explanation。看看你是否想以这种方式实现它。

另一个选项(如@Guna所述)是,你可以创建缓存的线程池,让执行者在线程上运行任务。

答案 1 :(得分:0)

您必须继续检查run方法中的标志。如果希望线程取消,可以将此标志设置为false。 下次run方法检查此标志时,因为它是false,因此它退出线程。 可能你想使用ThreadPoolExecutor?

答案 2 :(得分:0)

我发布了一个基于Java的纯代码,它也适用于android。使用android时,您需要注意不要从程序的一部分更新GUI,该程序在主GUI线程以外的线程中执行。如果您希望从另一个线程编辑GUI,则可以使用在主GUI线程中实例化的Handler。

定义此类模型的基本界面

/**
 * 
 * @author nits.kk
 * 
 * This defines the methods for the model.
 *
 */
public interface IResumable {
  /**
   * starts the model
   */
  public void requestStart();
  /**
   * requests the model to pause
   */
  public void requestPause();
  /**
   * requests the model to resume with new parameter
   * @param newParam
   */
  public void resumeWithNewParam(int newParam);
 /**
   * terminate the model
   */
  public void requestStop();
}

现在具体实现

public class ResumableModel implements IResumable {
  private Thread worker;
  private WorkerRunnable work;

  public ResumableModel(int initialValue) {
        work = new WorkerRunnable(initialValue);
        worker = new Thread(work);
  }

  @Override
  public void requestStart() {
        worker.start();
  }

  @Override
  public void requestPause() {
        work.setPauseRequested(true);
  }

  @Override
  public void resumeWithNewParam(int newParam) {
        work.setNewParam(newParam);
  }

  @Override
  public void requestStop() {
        worker.interrupt();
  }

  private static class WorkerRunnable implements Runnable {
        private int param; // we can have the variable of the type depending upon the requirement.
        private final Object lock = new Object();
        private volatile boolean isPauseRequested = false;

        public void run() {
              synchronized (lock) {
                    try {
                          while (!Thread.currentThread().isInterrupted()) {
                                while (isPauseRequested) {
                                      lock.wait();
                                }
                                System.out.println("value of param is" + param);
                          }
                    } catch (InterruptedException e) {
                          e.printStackTrace();
                    }
              }
        }

        public WorkerRunnable(int param) {
              this.param = param;
        }

        private void setPauseRequested(boolean isPauseRequested) {
              this.isPauseRequested = isPauseRequested;
        }

        private void setNewParam(int param) {
              // double locking to prevent the calling thread from being locked
              // (if in running state without pause requested then calling thread
              // will be in indefinite wait state for acquiring the lock.
              if (isPauseRequested) {
                    synchronized (lock) {
                          if (isPauseRequested) {
                                this.param = param;
                                this.isPauseRequested = false;
                                lock.notifyAll();
                          } else {
                                // logger will be used in real application
                                System.out.println("Need to pause first before setting a new param"); 
                          }
                    }
              } else {
                    // logger will be used in real application
                    System.out.println("Need to pause first before setting a new param"); 
              }
        }
  }
}

现在,当您希望启动线程时,您可以执行以下操作

IResumable resumable = new ResumableModel(10);
resumable.requestStart();

如果要暂停线程,只需调用requestPause()方法

即可
resumable.requestPause();

现在,当您需要使用新变量值恢复线程时,您可以调用resumeWithNewParam

resumable.resumeWithNewParam(20);

现在当你觉得你不需要线程和模型应该终止然后你可以调用resumable.requestStop();

答案 3 :(得分:-1)

您可以像这样创建线程类

public class AsyncThread extends Thread{
        @Override
        public void run() {
            super.run();
            //do your task
        }
    }

检查线程是否还活着

AsyncThread thread = new AsyncThread();
        if(thread.isAlive()){
            thread.interrupt();
           //do other stuff
        }else{
            thread.start();
        }