I couldn't find a question similar enough to this, but I do apologize if this is a duplicate.
//do something
//start
new Thread(r).start();
Runnable r = new Runnable() {
public void run() {
try{
Thread.sleep(5000);
//do something
}
catch(InterruptedException e){}
}
};//end new Runnable
My question is: Am I using a thread? or just a runnable object? Not sure if I am even asking a meaningful question?
I am new to threads, but my understanding of this code is : I am starting a new thread, passing it a runnable object, and it begins the overridden run method, in this case the thread will sleep for 5 seconds then do work.
Yes, you're using a Thread.
You create it by passing to its constructor a Runnable object.
"I am starting a new thread, passing it a runnable object, and it begins the overridden run method, in this case the thread will sleep for 5 seconds then do work."
This is correct, but the key point is missing: that this run method will be executed in another/new Thread, and not in the Thread from which you called start() on the Thread object which you created.
The Runnable interface just declares the fact that the class that implements it is able to be executed in a thread, so that it provides the interface to be called and executed by an external thread, nothing more.
A Thread implements Runnable since it's able to execute its own run() method but Runnable in general doesn't have anything related to threading itself. The default run() of Thread doesn't do anything, that's why you usually extend it and define the specific behavior of your thread.
But just to clarify, a ThreadPoolExecutor accepts Runnable objects exactly like a Thread. It's just the interface which declares that the class definition, is indeed, runnable (or executable).
You created a new anonymous implementation of Runnable interface.
This implementation povided the action to perform when executing the this implementation in a new Thread
You created a new Thread (new Thread(r)) and passed the anonymous instance to thread instance
When you started executing the thread (new Thread(r).start()), the jvm created a new thread. This new thread in turn invoked the run() method of the anonymous Runnable implementation.
An instance of Thread (as you create in the first line of code) represents a physical thread. When you call start(), the JVM will spawn a new thread (using the OS native methods to do so) and start its execution.
A Runnable is just an interface that defines the run() method (as you do in your second line of code). If you pass any object implementing Runnable to the Thread constructor, then the thread will run the code defined in the run() method.
Runnables are very lightweight since they only define one method, while Threads come with the heavy weight of a physical thread.
Directly creating a Thread is not recommended since it's an expensive operation. I highly recommend you look at the java Executors framework as it provides a flexible way of creating thread pools and submitting tasks (in the form of Runnables or Callables) to them. The Executors framework provides invaluable facilities for thread reuse.
Related
Let's say I have a runnable class with two methods:
class ExampleClass implements Runnable {
public void shutdown()
{
currentThread().interrupt();
}
public void run(){
while(!currentThread().isInterrupted()){
System.out.println("thread is running...");
}
}
And I go and implement the class somewhere like so and pass it to a thread:
ExampleClass object = new ExampleClass();
Thread sideThread = new Thread( object, "Side Thread");
thread.start();
object.shutdown();
Will all this object and all its methods be running on sideThread or is just the run() method of object on the side thread?
i.e. When I call shutdown() will it actually interrupt the sideThread or will it just interrupt on the main thread where the object is instantiated?
There's no additional magic in Runnable. A Thread takes a Runnable and calls its run method on a new thread. End of story. Any other methods on that object are none of Thread's business. If you want to provide tighter integration between the calling thread and the created thread, that's on you to design.
What Silvio Mayolo says is correct, any thread can call any method of an object, passing a Runnable to a thread's constructor tells the thread to execute that Runnable's run method. If you want you can pass the same object implementing Runnable to several new threads and let them all run it. No magic here.
When you call Thread.currentThread(), that returns the thread that is executing the code. So as your posted code works now, if 1) a thread A starts a new thread B passing in this Runnable, and next 2) thread A calls shutdown on the Runnable, the result is that the interrupt flag is set on thread A, not on the thread B, the one executing the run method. Probably not what you want. It would be better to keep a reference to the new thread, and call interrupt on that.
Each thread gets a name generated for it. Try adding some lines like:
System.out.println("thread=" + Thread.currentThread().getName());
in your code and it will show you which thread is executing. You will see the new thread executing the run method, and the thread that created the new thread running the shutdown method.
This question already has answers here:
What's the difference between Thread start() and Runnable run()
(14 answers)
Closed 8 years ago.
I was learning the concept of Multithreading in Java where I came across this very interesting behavior. I was experimenting with various ways of creating a thread. The one under question now is when we are extending a Thread, not implementing the Runnable interface.
On a side note, I am aware that it makes perfect OO sense to implement the Runnable interface rather than to extend the Thread class, but for the purposes of this question, let's say we extended the Thread class.
Let t be my instance of my extended Thread class and I have a block of code to be executed in the background that is written within my run() method of my Thread class.
It perfectly ran in the background with the t.start(), but I got a bit curious and called t.run() method. The piece of code executed in the main thread!
What does t.start() do that t.run() doesn't?
That is what the class does. The t.start() will actually start a new thread and then calls run() in that thread. If you directly invoke run() you run it in your current thread.
public class Test implements Runnable() {
public void run() { System.out.println("test"); }
}
...
public static void main(String...args) {
// this runs in the current thread
new Test().run();
// this also runs in the current thread and is functionally the same as the above
new Thread(new Test()).run();
// this starts a new thread, then calls run() on your Test instance in that new thread
new Thread(new Test()).start();
}
This is intended behavior.
The t.start() simply does what it says: starts a new thread, that executes the run()'s portion of code. t.run() is a function call on an object, from the current working thread (in your case, main thread).
Just keep in mind: only when call start() function of a thread, a new thread is started, otherwise, calling it's functions (other than start()) is the same as calling a plain function on any other different object.
t.start() makes a native call to actually execute the run() method in a new thread. t.run() merely executes the run() in the current thread.
Now,
On a side note, I am aware that it makes perfect OO sense to implement the Runnable interface than to extend the Thread class
Actually, it makes perfect OO sense to follow either approaches (implementing Runnable or extending Thread). It is not that one is bad in OO sense. The advantage that you get by implementing Runnable is that you can make your class extend another class (which might actually break your OO design.)
I was recently reading about creation of Threads in java by implementing Runnable or Extending thread and last Implementing Callable. Runnable Versus Callable thread at stackoverflow describes the difference quoting both are designed for classes whose instances are potentially executed by another thread. What does it mean? Does it creates new Thread? If yes, why we need to pass a class that implements Runnable to Thread constructor?
Also, i saw the method of creating threads by implementing Runnable or Extending thread. In the first method, (in the tutorials what i found), we need to call Thread class which requires the Runnable instance to start the thread. But, i could not found the similar thing for Callable as there is no Thread constructor which accepts Callable. Executor framework or Future Task is used for the purpose of running those threads. Then why we say both ways are same (except Callable retruns something and can throw Exception).
Last, is writing
Thread t = new Thread();
Thread t1 = new Thread(new RunnableInstance());
Do these create new Threads in system? Is there any other way of using Runnable to create new threads without passing it as a constructor to Thread class?
It should not be a duplicate question.
What does it mean? Does it creates new Thread?
Both Callable and Runnable are just interfaces, they don't create any threads by themself. Instead they provide API and abstractions for developers. When you want to execute some code in separate thread you typically implement Runnable and then you can decide how to execute this. It is not bound to any thread yet. You have many options actually:
Execute it in the new Thread
Execute it with some ExecutorService
Or just call it directly
If yes, why we need to pass a class that implements Runnable to Thread constructor?
No.
Since Runnable does not create thread behind (well, it simply can't since it's just an interface!), we need to execute this Runnable explicitly.
Do these create new Threads in system?
Yes.
Is there any other way of using Runnable to create new threads without passing it as a constructor to Thread class?
Yes. I mentioned already ExecutorService. You can profit from thread pool or completion service, take a look at the API and examples.
Callable
It will return the result of the execute.
Runnable
It wont return. But it will run separately like callable.
Extends Thread
Its also a runnable. But if you extend thread , you cant extend any class since java wont support multiple inheritance.
Callable and Runnable provides interfaces for other classes to execute them in threads. They contain no functionality of their own. The most common way to do this is via an ExecutorService. Have a look at the classes available in java.until.concurrent. There are many options there. Extending Thread is not really called for unless you really intend to add new low-level threading functionality.
In java, does run() register a thread in a thread scheduler?
What about construct(),start() and register() ?
In java, does run() register a thread in a thread scheduler?
No. If you call the run() method directly, it is called as a normal method; i.e. it runs on the current thread, not a new one.
What about construct(),start() and register()
The start method creates a new thread, and in the process the thread will be registered with the scheduler. (However, the scheduler is a nebulous concept in Java. It is implied that one must exist, but its implementation and behavior are typically left to the host operating system. A pure Java program has almost no control over the way that the thread scheduler actually works.)
There are no construct() or register() methods in the Thread API. If you are referring to the Thread constructors, they only create a Thread object, and NOT the underlying thread that will do the work. The latter is only created when start() is called.
run() is the actual code in the thread; so you could do like:
Thread childThread = new Thread() {
public void run() {
// do stuff on a new thread
}
};
(Though I've been told extending Thread like that is ugly ;)
So calling run() itself won't create a new thread. To do that, you use start():
childThread.start();
So, I guess it does give the scheduler a new thread to deal with -- but that's way down on the OS level.
I'm not sure what you mean by construct() and register() though?
Or is it?
I have a thread object from:
Thread myThread = new Thread(pObject);
Where pObject is an object of a class implementing the Runnable interface and then I have the start method called on the thread object like so:
myThread.start();
Now, my understanding is that when start() is called, the JVM implicitly (and immediately) calls the run() method which may be overridden (as it is in my case)
However, in my case, it appears that the start() method is not called immediately (as desired) but until the other statements/methods are completed from the calling block i.e. if I had a method after the start() call like so:
myThread.start();
doSomethingElse();
doSomthingElse() gets executed before the run() method is run at all.
Perhaps I am wrong with the initial premise that run() is always called right after the start() is called. Please help! The desired again is making executing run() right after start(). Thanks.
Um... the run() method will run in a different thread. That, per definition, means you cannot make any assumptions about before or after which statements in the current thread it will execute, unless you synchronize them explicitly.
Now, my understanding is that when start() is called, the JVM implicitly (and immediately) calls the run() method ...
That is incorrect. It does implicitly call run(), but the call does not necessarily happen immediately.
The reality is that the new thread becomes available to be scheduled at some point in time after the start() call is made. The actual scheduling is up to the native scheduler. It could happen immediately, or the parent thread could continue for a period before the child thread is scheduled.
To force your thread to start running immediately (or to be more accurate, to start running before doSomethingElse()), you need to do some explicit synchronization; e.g. something like this:
java.util.concurrent.CountDownLatch latch = new CountdownLatch(1);
new Thread(new MyRunnable(latch)).start();
latch.await(); // waits until released by the child thread.
doSomethingElse();
where
class MyRunnable implements Runnable {
private CountDownLatch latch;
MyRunnable (CountDownLatch latch) { this.latch = latch; }
public void run() {
doSomeStuff();
latch.countDown(); // releases the parent thread
doSomeMoreStuff();
}
...
}
There are other ways to implement the synchronization using the concurrency classes, or Java's mutex / wait / notify primitives1. But explicit synchronization between the two threads is the only way to guarantee the behavior that you require.
Note that the doSomething() call in the child thread will complete before the parent thread is released, but we can say nothing about the order of execution of doSomethingElese() and doSomeMoreStuff(). (One might run before the other and vice versa, or they might run in parallel.)
1 - Using wait / notify is not recommended, but it may be your only option if the concurrency APIs are not available; e.g. on Java ME.
run() is the first thing within your code that the new thread does, but there's some set-up work that the new thread does first, and there's no guarantee that any significant amount of work will by done by the new thread before the original thread goes on to call doSomethingElse().
You're right in thinking that there are no guarantees here. Making assumptions about the behaviour of multithreaded code is the source of much pain - try not to do it!
When you call myThread.start(), your thread becomes available for execution. Whether it will actually gain CPU, and for how long -- it's up the the OS scheduler. In fact, your run() may be getting control immediately, but losing it before it can do anything you can notice. The only way to ensure that your thread executes what you need before doSomethingElse() is to use explicit synchronization.
You've started a new thread. That thread runs in parallel to the thread that started it so the order could be:
pObject.run();
doSomethingElse();
or
doSomethingElse();
pObject.run();
or, more likely, there will be some crossover. pObject.run() may run in the middle of doSomethingElse() or vice versa or one will start before the other finishes and so on. It's important to understand this and understand what is meant by an atomic operation or you will find yourself with some really hard-to-find bugs.
It's even more complicated if two or more threads access the same variables. The value in one may never be updated in one thread under certain circumstances.
I highly suggest:
You don't make your program multi-threaded unless you absolutely need to; and
If you do, buy and read from cover to cover Brian Goetz's Java Concurrency in Practice.
calling the start method on a Thread Object may not make the jvm invoke the run() method immidiately, rather it makes the thread a runnable and ready for execution, in this case the parent thread first executes its code and then passes control to the child thread, if u want the child thread to execute before the parent thread code is executed use the chileThreadObject.join() method in the parent thread.