【问题标题】:How can one thread tell another thread to stop?一个线程如何告诉另一个线程停止?
【发布时间】:2018-03-30 18:37:02
【问题描述】:

我正在制作一个在 Oncreate 方法中创建线程的服务。这个线程是一个无限循环,播放一个 MP3 文件,进入休眠状态 30 秒。

我正在尝试找出如何在 onDestroy 方法中阻止这种情况

代码

公共无效 onCreate() { Toast.makeText(this, "Service Created", Toast.LENGTH_LONG).show();

    mediaPlayer = MediaPlayer.create(this, R.raw.nysound);
    mThread=new myThread();
    mThread.start();
}

public class myThread extends Thread {

    public void run() {
        do{
            mediaPlayer.start();
            try
            {
                Thread.sleep(1000*20);
            } catch(Exception e)
            {
                ted++;
            }

        } while(true);
    }  // end methed
} // end class

@Override
public void onDestroy() {
    Toast.makeText(this, "Service Stopped", Toast.LENGTH_LONG).show();

}

【问题讨论】:

  • 奇数大写是怎么回事?
  • 另外,try..catchThread.sleep() 附近是怎么回事?

标签: java android


【解决方案1】:

您可以为此使用 boolean 标志

public class myThread extends Thread {

  private volatile boolean running = true;
  public void run() {
    do{
        mediaPlayer.start();
        try
        {
            Thread.sleep(1000*20);
        } catch(Exception e)
        {
            ted++;
        }

    } while(running);
  }  // end methed

  public void setRunning(boolean newValue) {
    this.running = newValue;
  }
} //

然后在主线程中执行以下操作

@Override
public void onDestroy() {
  mThread.setRunning(false);
  Toast.makeText(this, "Service Stopped", Toast.LENGTH_LONG).show();

}

【讨论】:

  • 这就是我的想法,但我必须等待睡眠结束。看起来这是唯一的保存方法。
  • @Tedpottel,您也可以使用mThread.interrupt(),但在这种情况下,您需要在循环中以不同方式处理InterruptedException,例如catch(InterruptedException in) {running = false}
【解决方案2】:

调用 onDestroy() 不是停止服务的正确方法

系统调用 public void onDestroy() 来通知服务它不再使用并且正在被移除。此时服务应该清理它持有的所有资源(线程、注册的接收器等)。返回后,将不再调用此 Service 对象,它实际上已死。不要直接调用此方法。

如果你在服务类,请调用方法

stopSelf();

如果你在另一个班级,比如你的 MusicPlayerActivity 调用下面的代码

Intent i = new Intent(this, ServiceName.class); 停止服务(i);

这两个都会停止你的服务。

【讨论】:

    【解决方案3】:

    您应该考虑使用更高级别的对象 ScheduledExecutorService 来处理线程执行:

     public void onCreate() { Toast.makeText(this, "Service Created", Toast.LENGTH_LONG).show();
    
            mediaPlayer = MediaPlayer.create(this, R.raw.nysound);
            ScheduledExecutorService ses = 
            Executors.newScheduledThreadPool(1);
            scheduledFuture = ses.scheduleWithFixedDelay(new MyThread(), 0, 20, TimeUnit.SECONDS);
    
        }
    
        public class myThread extends Thread {
    
            public void run() {
                    mediaPlayer.start();
            }  // end methed
        } // end class
    
        @Override
        public void onDestroy() {
            Toast.makeText(this, "Service Stopped", Toast.LENGTH_LONG).show();
            scheduledFuture.cancel(true);
    
        }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-09-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多