How to Stop a Thread Created by Implementing Runnable Interface

How to stop a thread created by implementing runnable interface?

The simplest way is to interrupt() it, which will cause Thread.currentThread().isInterrupted() to return true, and may also throw an InterruptedException under certain circumstances where the Thread is waiting, for example Thread.sleep(), otherThread.join(), object.wait() etc.

Inside the run() method you would need catch that exception and/or regularly check the Thread.currentThread().isInterrupted() value and do something (for example, break out).

Note: Although Thread.interrupted() seems the same as isInterrupted(), it has a nasty side effect: Calling interrupted() clears the interrupted flag, whereas calling isInterrupted() does not.

Other non-interrupting methods involve the use of "stop" (volatile) flags that the running Thread monitors.

How to stop a runnable within the runnable?

You can break the loop if health < 1:

if (health < 1) {
break;
}

Or you can change the while condition:

while (health > 1) {

}

How to Sleep() or wait() a thread created by implementing runnable interface?

You could tell the philosophers to wait at an appropriate point in their run() method and then notify them to resume:

boolean waitRequested = false;

void requestWait() {
waitRequested = true;
}

void resume() {
synchronized(this) {
notify();
}
}

public void run() {
while( condition ) {
try {
//check if the thread should wait first, if not let it do a full iteration of the loop
if( waitRequested ) {
synchronized( this ) {
wait();

//resuming here so wait wouldn't be requested anymore
waitRequested = false;
}
}

//do whatever a philosopher does
}
catch( InterruptedException e) {
//handle exception
}
}
}

Then call requestWait() and resume() on the objects. Note that you could just call notify() on the objects but you'd then have to surround that with a synchronized block or otherwise you'll most certainly get a IllegalMonitorStateException since the thread that's calling notify() is most likely not the current owner of the monitor.

How do i stop a Runnable thread or interface

There is only one way to properly stop thread: from this thread's code, by leaving run() method. Most popular ways to achieve this:

  1. Volatile flag - useful when your thread does CPU work

    volatile boolean stop = false
    void run() {
    doComputation();
    if (stop) return;
    doAnotherComputation();
    if (stop) return;
    doMoreComputation();
    }
  2. interruption - when your thread mostly sleeps on locks

    void run() {
    synchronized(lock) {
    lock.wait(); //wait() will throw InterruptedException here
    }
    }
    //from another thread
    myThread.interrupt();`

As a consequence, if you are calling library code which takes long time and does not react to interrupt(), this code cannot be aborted correctly to stop thread it is running in.

Interrupting a Runnable with a method of the class

What you want to do - implementing a stop() method inside a Runnable - may actually introduce some confusion in the structure of your code. Why? A Runnable object is, by design, something which holds the code that has to run. But adding a stop() method would go beyond the sole responsibility of a Runnable object: that is, you will make it able to control the execution of your code. That should be avoided.

Here is a hint: there is no start() method in Runnable. Indeed, there is one in the Thread class, and the Runnable interface has been introduced in the JDK to reduce coupling between the "runnable" code and the object which controls its execution (an instance of Thread).

My question is: why aren't you satisified with the future.cancel()? Could you please add some precisions in your design requirements?

Running many thread and Stop thread on Exception

You face multiple problems here:

  1. You cannot join a thread in itself. Thread.join() waits until the thread dies. But if you call it from the thread you want to stop, it just waits forever.

  2. To stop a thread you simply have to return from its run() method. In your case, just add return in your catch clause instead of calling closeThread().

  3. It seems that you have some memory problems. Either whatever you do in exportCorner() uses alot of memory or you create to many threads at once. As Andy Turner has mentioned in the comments, it might be usefull to use an ExecutorService to handle your Runnables. This may help you managing your threads and ensure a limited thread count.

How to stop or exit Runnable

Edit:

Now that you've added code that involves the Handler it's now clearer where your trouble lies. Some points to understand:

  • Android has a general concept that there is the main thread and then there are many other threads.
  • Only the main thread may modify the UI
  • In later versions of android the main thread is not allowed to do networking...

So how to change the UI based on reading something from the network?

You need to pass a message from another (networking) thread to the main thread. The Handler let's your other thread give a message to the main thread... That is your networking thread can give a task (Runnable) to the main thread to perform. The handler posts the task from the networking thread to the main thread.

protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
intent = getIntent();
setContentView(R.layout.activity_display_message);
message = intent.getStringArrayExtra(MainActivity.EXTRA_MESSAGE);
newtext = (TextView)findViewById(R.id.TextView1);
userName = message[0];
serverIP = message[1];
sendConnectionRequest ();
mHandler = new Handler(); // Handler to update UI
// This is being created in the main thread
// so everything posted will be posted to
// the main thread

mUpdate.start(); // start thread to do something on the network
//before updating the UI

}

public Thread mUpdate = new Thread() {
public void run() {
try {
while (!thread.interrupted()) {
final String line = in.readLine();
Log.i("RESPONSE FROM SERVER", "S: Received Message: '" +line+ "'");

// Define the UI change you want to make
Runnable uiUpdate = new Runnable() {
public void run() {
// modify your UI here.
newtext.setText(line);
}
};

// post the UI change back to the main thread.
mHandler.post(uiUpdate);
}
} catch (IOException e) {
// TODO Auto-generated catch block
Log.e("Error" , "Something Happen");
}
}

public void interrupt() {
try {
super.interrupt();
in.close();
}
catch (IOException e) {}
}
};

May I suggest you also:

protected void onDestroy() {
mUpdate.interrupt();
}

Original Answer (Now defunct)

From my understanding, buttons are on UI thread and Runnable is a separate thread and that's why it doesn't respond to button press immediately coz its busy on separate thread.

That's not correct at all.
A Thread is a separate thread not a Runnable. And you need to call start() not run() on the thread to make the run method execute in its own thread. The whole point of using threads is that one thread will not (usually) be blocked by another being busy.

// <snip>removed for brevity of new answer</snip>

You can also look into an AsyncTask from the android library. This will also run in its own thread if you use it correctly.

Why does Thread Class implements Runnable Interface

"The Runnable interface should be implemented by any class whose instances are intended to be executed by a thread. [...]
This interface is designed to provide a common protocol for objects that wish to execute code while they are active. For example, Runnable is implemented by class Thread."

oracle doc

But I think what your exactly looking for is here. The answer given was "backward compability".
Sometimes Java needs to make choices, and they always chose solutions dealing with backward compability.

Stop java thread without a reference to it

You could include an atomic boolean flag in that object that is passed to the constructor, and poll it from the thread. If the shutdown flag is set, the thread can shut down.

That can be describe as a cooperative shutdown protocol.



Related Topics



Leave a reply



Submit