I realized that this code:
public class TestThread3 extends Thread {
private int i;
public void run() {
i++;
}
public static void main(String[] args) {
TestThread3 a = new TestThread3();
a.run();
System.out.println(a.i);
a.start();
System.out.println(a.i);
}
}
results in 1 1 printed ... and i don't get it. I haven´t found information about how to explain this. Thanks.
results in 1 1 printed
So the first a.run(); is called by the main-thread directly by calling the a.run() method. This increments a.i to be 1. The call to a.start(); then is called which actually forks a new thread. However, this takes time to do so the i++; operation most likely has not started before the System.out.println(...) call is made so a.i is still only 1. Even if the i++ has completed in the a thread before the println is run, there is nothing that causes the a.i field to be synchronized between the a thread and the main-thread.
If you want to wait for the spawned thread to finish then you need to do a a.join(); call before the call to println. The join() method ensures that memory updates done in the a thread are visible to the thread calling join. Then the i++ update will be seen by the main-thread. You could also use an AtomicInteger instead of a int which wraps a volatile int and provides memory synchronization. However, without the join() there is still a race condition between the a thread doing the increment and the println.
// this provides memory synchronization with the internal volatile int
private AtomicInteger i;
...
public void run() {
i.incrementAndGet();
}
...
a.start();
// still a race condition here so probably need the join to wait for a to finish
a.join();
System.out.println(a.i.get());
This behavior can change at any point of time because when a.start() is called, the thread is scheduled for process, not necessary the OS will let it start executing on CPU.
Once a.start() returns, you actually have two threads (one is for main and another is a new thread), and the main would still be running.
The expected result could only come if following happens,
Time
T1 main method calls a.start()
T2 jvm / os schedules thread for execution
T3 a.start() returns and main thread gets context-switched and suspended for other threads.
T4 Spawned thread gets execution context, and its run method is called, which increments value
T5 context switch happens and main thread gets the control back
T6 main thread would print 2
Jatan
You have two main issues here to clear up. I also recommend you examine Gray's answer for more technical information.
**Note: This just skims the surface, but most of the other answers take for granted the background knowledge on these Computer Science topics that I believe you have not yet mastered.
First, threads are not guaranteed order of execution. In general, you should only use threads if they can work asynchronously (independently timed). For this example, you have a timing-specific expected outcome, so threading should probably just be avoided.
This, however, isn't your only issue.
As is, your code also has what is called a Race Condition. A Race Condition occurs when two different threads (or processes) have access to read/manipulate the same data -- In your case, reading i and incrementing via i++.
For example,
Imagine that you and a friend both have a dollar. The Ice Cream Man drives along and stops in front of you. The Ice Cream Man only has one ice cream cone left. There are a couple of ways this could play out:
You are faster than your friend and buy the cone first.
You are slower than your friend and he buys the cone first.
You decide to split the ice cream cone and both pay $0.50.
You two fight and someone else gets to buy the last ice cream cone while you two are distracted.
To mirror this back to the computer,
The main thread where you are printing continues to run even after you started the second thread. (Threads are linked to the same process, so when main returns, the other threads "die". It is possible the thread, even though it a.start()'ed, doesn't finish or may not even get a chance to run at all!)
The other thread gets to run and completes before returning to the main thread.
You take turns executing and everyone gets to do a few lines of code. The out come is really asynchronous here. And this can very likely happen.
The java application process loses the CPU and someone else gets to run (potentially accessing similar shared information.)
TL;DR -
If you want to ensure execution order, then just DO NOT use threads.
There are some cases where syncing up at certain points along the way would be nice. For these cases, you can join the threads (wait for one to finish before continuing), or lock the Race Condition with a Mutex or Semaphore (more advanced synchronization techniques).
I recommend doing some reading on these topics before attempting to jump into battle with the monstrous operating system.
Related
I am making an online game in Java and I ran into one particular issue where I was trying to find the most efficient way to send clients spawn entity NPC packets. I of course understand how to send them but I wanted to do it off of the main game loop since it requires looping through a map of NPC's (I also made sure its thread safe). To do this I thought a BlockingQueue was my best option so I created a new thread set it to daemon then passed in a runnable object. Then whenever I needed to send one of these packets I would use the insertElement() method to add to the queue. Here is how it looks.
public class NpcAsyncRunnable implements Runnable {
private final BlockingQueue<NpcObject> blockingQueue;
public NpcAsyncRunnable() {
blockingQueue = new LinkedBlockingQueue<>();
}
#Override
public void run() {
while(true) {
try {
final NpcObject obj = blockingQueue.take();
//Run my algorithm here
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
public void insertElement(final NpcObject obj) {
blockingQueue.add(obj);
}
}
Now my question is how efficient is this? I am running the thread the whole time in an infinite loop because I always want it to be checking for another inserted element. However, my concern is if I have too many async threads listening would it start to clog up the CPU? I ask this because I know a CPU core can only run 1 thread of execution at a time but with hyperthreading (AMD has the same thing but its called something different) it can jump between executing multiple threads when one needs to search for something in memory. But does this infinite loop without making it sleep mean it will always be checking if the queue has a new entry? My worry is I will make a CPU core waste all its resources infinitely looping over this one thread waiting for another insertion.
Does the CPU instead auto assign small breaks to allow other threads to execute or do I need to include sleep statements so that this thread is not using way more resources than is required? How much CPU time will this use just idling?
...does this infinite loop without making it sleep mean...?
blockingQueue.take() does sleep until there's something in the queue to be taken. The Javadoc for the take method says, "Retrieves and removes the head of this queue, waiting if necessary until an element becomes available."
"Waiting" means it sleeps. Any time you are forced to write catch (InterruptedException...), it's because you called something that sleeps.
how does it know when something is added if its sleeping? It has to be running in order to check if something has been added to the queue right?
No. It doesn't need to run. It doesn't need to "check." A BlockingQueue effectively* uses object.wait() to make a thread "sleep," and it uses object.notify() to wake it up again. When one thread in a Java program calls o.wait() for any Object o, the wait() call will not return** until some other thread calls o.notify() for the same Object o.
wait() and notify() are thin wrappers for operating system-specific calls that do approximately the same thing. All the magic happens in the OS. In a nutshell;
The OS suspends the thread that calls o.wait(), and it adds the thread's saved execution context to a queue associated with the object o.
When some other thread calls o.notify(), the OS takes the saved execution context at the head of the queue (if there is one***), and moves it to the "ready-to-run" queue.
Some time later, the OS scheduler will find the saved thread context at the head of the "ready-to-run" queue, and it will restore the context on one of the system's CPUs.
At that point, the o.wait() call will return, and the thread that waited can then proceed to deal with whatever it was waiting for (e.g., an NpcAsyncRunnable object in your case.)
* I don't know whether any particular class that implements BlockingQueue actually uses object.wait() and object.notify(), but even if they don't use those methods, then they almost certainly use the same operating system calls that underlie wait() and notify().
** Almost true, but there's something called "spurious wakeup." Correctly using o.wait() and o.notify() is tricky. I strongly recommend that you work through the tutorial if you want to try it yourself.
*** o.notify() does absolutely nothing at all if no other thread is already waiting at the moment when it is called. Beginners who don't understand this often ask, "Why did wait() never return?" It didn't return because the thread that wait()ed was too late. Again, I urge you to work through the tutorial if you want to learn how to avoid that particular bug.
I am having an issue ending threads once my program my has finished. I run a threaded clock object and it works perfectly but I need to end all threads when the time ´==´ one hour that bit seems to work I just need to know how to end them. Here is an example of the code I have and this is the only thing that runs in the run method apart from one int defined above this code.
#Override
public void run()
{
int mins = 5;
while(clock.getHour() != 1)
{
EnterCarPark();
if(clock.getMin() >= mins)
{
System.out.println("Time: " + clock.getTime() + " " + entryPoint.getRoadName() + ": " + spaces.availablePermits() + " Spaces");
mins += 5;
}
}
}
But when you keep watching the threads that are running in the debug mode of netbeans they keep running after an hour has passed not sure how to fix this. I have tried the interrupt call but it seems to do nothing.
There are two ways to stop a thread in a nice way, and one in an evil way.
For all you need access to the object of the thread (or in the first case a Runnable class that is executed on that thread).
So your first task is to make sure you can access a list of all threads you want to stop. Also notice that you need to make sure you are using threadsafe communication when dealing with objects used by several threads!
Now you have the following options
Interrupt mechanisme
Call Thread.interrupt() on each thread. This will throw an InterruptedException on the thread if you are in a blocking function. Otherwise it will only set the isInterrupted() flag, so you have to check this as well. This is a very clean and versatile way that will try to interrupt blocking functions by this thread. However many people don't understand how to nicely react to the InterruptedException, so it could be more prone to bugs.
isRunning flag
Have a boolean 'isRunning' in your thread. The while loop calls a function 'stopRunning()' that sets this boolean to false. In your thread you periodically read this boolean and stop execution when it is set to false.
This boolean needs to be threadsafe, this could be done by making it volatile (or using synchronized locking).
This also works well when you have a Runnable, which is currently the advised way of running tasks on Threads (because you can easily move Runnables to Threadpools etc.
Stop thread (EVIL)
A third and EVIL and deprecated way is to call Thread.stop(). This is very unsafe and will likely lead to unexpected behavior, don't do this!
Make sure that the loop inside every thread finishes - if it does in all the threads, it does not make sense that there are prints in the output. Just note that what you are checking in each loop condition check if the current hour is not 1 PM, not if an hour has not passed.
Also, your threads garbage collected, which means that the Garbage Collector is responsible for their destruction after termination - but in that case they should not output anything.
A volatile variable shared by all the Threads should help to achieve the goal. The importance of a volatile variable is that each of the Threads will not cache or have local copy but will need to directly read from the main memory. Once it is updated, the threads will get the fresh data.
public class A{
public static volatile boolean letThreadsRun = true;
}
// inside your Thread class
#Override
public void run()
{ // there will come a point when A.letThreadsRun will be set to false when desired
while(A.letThreadsRun)
{
}
}
If two threads are both reading and writing to a shared variable, then
using the volatile keyword for that is not enough. You need to use
synchronization in that case to guarantee that the reading and writing
of the variable is atomic.
Here are links that may help you to grasp the concept:
http://tutorials.jenkov.com/java-concurrency/volatile.html
http://java.dzone.com/articles/java-volatile-keyword-0
If these threads are still running after your main program has finished, then it may be appropriate to set them as daemon threads. The JVM will exit once all non-daemon threads have finished, killing all remaining daemon threads.
If you start the threads like:
Thread myThread = new MyThread();
myThread.start();
Then daemon-izing them is as simple as:
Thread myThread = new MyThread();
myThread.setDaemon(true);
myThread.start();
It's a bad practice to externally terminate threads or to rely on external mechanisms like kill for proper program termination. Threads should always be designed to self-terminate and not leave resources (and shared objects) in a potentially indeterminate state. Every time I have encountered a thread that didn't stop when it was supposed to, it was always a programming error. Go check your code and then step through the run loop in a debugger.
Regarding your thread, it should self-terminate when the hour reaches 1, but if it is below or above 1, it will not terminate. I would make sure that clock's hour count reaches one if minutes go past 59 and also check that it doesn't somehow skip 1 and increment off in to the sunset, having skipped the only tested value. Also check that clock.getHour() is actually returning the hour count instead of a dummy value or something grossly incorrect.
Have you considered using an ExecutorService ? It behaves more predictably and avoids the overhead of thread creation. My suggestion is that you wrap your while loop within one and set a time limit of 1 hr.
Using Thread.interrupt() will not stop the thread from running, it merely sends a signal to you thread. It's our job to listen for this signal and act accordingly.
Thread t = new Thread(new Runnable(){
public void run(){
// look for the signal
if(!Thread.interrupted()){
// keep doing whatever you're doing
}
}
});
// After 1 hour
t.interrupt();
But instead of doing all this work, consider using an ExecutorService. You can use Executors class with static methods to return different thread pools.
Executors.newFixedThreadPool(10)
creates a fixed thread pool of size 10 and any more jobs will go to queue for processing later
Executors.newCachedThreadPool()
starts with 0 threads and creates new threads and adds them to pool on required basis if all the existing threads are busy with some task. This one has a termination strategy that if a thread is idle for 60 seconds, it will remove that thread from the pool
Executors.newSingleThreadExecutor()
creates a single thread which will feed from a queue, all the tasks that're submitted will be processed one after the other.
You can submit your same Runnable tasks to your thread pool. Executors also has methods to get pools to which you can submit scheduled tasks, things you want to happen in future
ExecutorService service = Executors.newFixedThreadPool(10);
service.execute(myRunnableTask);
Coming to your question, when you use thread pools, you have an option to shut down them after some time elapsed like this
service.shutdown();
service.awaitTermination(60, TimeUnit.MINUTES);
Few things to pay attention
shutdown() Initiates an orderly shutdown in which previously submitted tasks are executed, but no new tasks will be accepted. Invocation has no additional effect if already shut down.
awaitTermination() is waiting for the state of the executor to go to TERMINATED. But first the state must go to SHUTDOWN if shutdown() is called or STOP if shutdownNow() is called.
So far what I have understood about wait() and yield () methods is that yield() is called when the thread is not carrying out any task and lets the CPU execute some other thread. wait() is used when some thread is put on hold and usually used in the concept of synchronization. However, I fail to understand the difference in their functionality and i'm not sure if what I have understood is right or wrong. Can someone please explain the difference between them(apart from the package they are present in).
aren't they both doing the same task - waiting so that other threads can execute?
Not even close, because yield() does not wait for anything.
Every thread can be in one of a number of different states: Running means that the thread is actually running on a CPU, Runnable means that nothing is preventing the thread from running except, maybe the availability of a CPU for it to run on. All of the other states can be lumped into a category called blocked. A blocked thread is a thread that is waiting for something to happen before it can become runnable.
The operating system preempts running threads on a regular basis: Every so often (between 10 times per second and 100 times per second on most operating systems) the OS tags each running thread and says, "your turn is up, go to the back of the run queue' (i.e., change state from running to runnable). Then it lets whatever thread is at the head of the run queue use that CPU (i.e., become running again).
When your program calls Thread.yield(), it's saying to the operating system, "I still have work to do, but it might not be as important as the work that some other thread is doing. Please send me to the back of the run queue right now." If there is an available CPU for the thread to run on though, then it effectively will just keep running (i.e., the yield() call will immediately return).
When your program calls foobar.wait() on the other hand, it's saying to the operating system, "Block me until some other thread calls foobar.notify().
Yielding was first implemented on non-preemptive operating systems and, in non-preemptive threading libraries. On a computer with only one CPU, the only way that more than one thread ever got to run was when the threads explicitly yielded to one another.
Yielding also was useful for busy waiting. That's where a thread waits for something to happen by sitting in a tight loop, testing the same condition over and over again. If the condition depended on some other thread to do some work, the waiting thread would yield() each time around the loop in order to let the other thread do its work.
Now that we have preemption and multiprocessor systems and libraries that provide us with higher-level synchronization objects, there is basically no reason why an application programs would need to call yield() anymore.
wait is for waiting on a condition. This might not jump into the eye when looking at the method as it is entirely up to you to define what kind of condition it is. But the API tries to force you to use it correctly by requiring that you own the monitor of the object on which you are waiting, which is necessary for a correct condition check in a multi-threaded environment.
So a correct use of wait looks like:
synchronized(object) {
while( ! /* your defined condition */)
object.wait();
/* execute other critical actions if needed */
}
And it must be paired with another thread executing code like:
synchronized(object) {
/* make your defined condition true */)
object.notify();
}
In contrast Thread.yield() is just a hint that your thread might release the CPU at this point of time. It’s not specified whether it actually does anything and, regardless of whether the CPU has been released or not, it has no impact on the semantics in respect to the memory model. In other words, it does not create any relationship to other threads which would be required for accessing shared variables correctly.
For example the following loop accessing sharedVariable (which is not declared volatile) might run forever without ever noticing updates made by other threads:
while(sharedVariable != expectedValue) Thread.yield();
While Thread.yield might help other threads to run (they will run anyway on most systems), it does not enforce re-reading the value of sharedVariable from the shared memory. Thus, without other constructs enforcing memory visibility, e.g. decaring sharedVariable as volatile, this loop is broken.
The first difference is that yield() is a Thread method , wait() is at the origins Object method inheritid in thread as for all classes , that in the shape, in the background (using java doc)
wait()
Causes the current thread to wait until another thread invokes the notify() method or the notifyAll() method for this object. In other words, this method behaves exactly as if it simply performs the call wait(0).
yield()
A hint to the scheduler that the current thread is willing to yield its current use of a processor. The scheduler is free to ignore this hint.
and here you can see the difference between yield() and wait()
Yield(): When a running thread is stopped to give its space to another thread with a high priority, this is called Yield.Here the running thread changes to runnable thread.
Wait(): A thread is waiting to get resources from a thread to continue its execution.
I have code like this:
public class OtherClass {
// OtherClass
public synchronized static void firstMethod() {
System.out.println("FIRST METHOD");
}
public synchronized static void secondMethod() {
System.out.println("SECOND METHOD");
// In actual code I would have try catch for this but here I just didn't
// include it
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
public class MainClass {
// main method of MainClass
public static void main(String args[]) {
Thread firstThread = new Thread() {
public void run() {
while (true) {
OtherClass.firstMethod();
}
}
};
Thread secondThread = new Thread() {
public void run() {
while (true) {
OtherClass.secondMethod();
}
}
};
secondThread.start();
firstThread.start();
}
}
The reason I start the 2nd thread first is because I want the secondMethod of OtherClass to execute first. I should see "FIRST METHOD" and "SECOND METHOD" in the console output every 5 seconds. The reason being is that since Thread.sleep does not relinquish the lock, for 5 seconds the first thread doesn't have access to the first method because the second thread has got a lock on the class while it's in the second method which tells the thread to sleep for 5 seconds. But I get very unexpected results. All I get in the console output is "SECOND METHOD" every 5 seconds. The firstMethod isn't called.
Ignoring compilation problems in your code.
That's just coincidence. The thread scheduler simply decides to continue executing the second thread which reacquires the lock too fast.
Run it long enough (or with a shorter sleep time for faster results) and you'll see the other method get invoked.
The reason I start the 2nd thread first is because I want the secondMethod of OtherClass to execute first.
That's not how threads work. That's not what threads are for. Threads provide no guarantees of what happens before what else except where you provide explicit synchronization between them; And generally speaking, the more synchronization you use, the less you will benefit from having multiple threads.
In your example, you have explicit synchronization that prevents any concurrent executions of firstMethod() and secondMethod(), but you have nothing that guarantees which one will run first, and which one will run second. Chances are, that main() will terminate before either of them runs. At that point, it's up to the scheduler to pick which one will run when. There is no requirement that it start them in the same order that your code called their start() methods.
Your example may be educational, but it also is an example of when not to use threads. Your synchronization is very heavy handed. Your program basically does two things, firstMethod() and secondMethod(), and the synchronization insures that they can not be overlapped. In production software, if you have two tasks that must not overlap, then it'll simplify your program's logic if they are always performed by the same thread.
All I get in the console output is "SECOND METHOD" every 5 seconds. The firstMethod isn't called.
Your question was edited before I got to see it, so I don't know whether you're talking about the original version, or the fixed version. But in any case:
The synchronization in your program does not guarantee that the two threads take turns. All it does is prevent them both from printing at the same time.
Each of your threads runs a loop that grabs the lock, prints something, releases the lock, and then immediately tries to grab the lock again. When a running thread releases a lock, and then immediately tries to get it again, the chances are it will succeed. It doesn't matter that some other thread was waiting for the lock. The OS doesn't know what your program is trying to accomplish, but it does know that it can make more efficient use of the CPU by letting a thread continue to run instead of blocking it and un-blocking some other thread.
You will need to use some additional synchronization to make the threads take turns, but like I said, in a real program, the more synchronization you use, the less benefit there is to using threads.
Your processor won't execute your Threads at the same time; it'll run your second thread every time bevore your first thread.
The behaviour is clear: Your processor executes your second thread. Then, the processor executes your first thread and sees that it is locked by your second thread. After 5 seconds, your second thread is called again. It makes the output, releases the lock and locks it again. If your first thread is called again, it is locked again.
To fix this, add Thread.yield() at the end of your while. This will make the processor call the first thread before continuing to execute your second thread (the first thread won't be the only one that is called, it just removes your second thread 1 time from it's execution). Then your first thread gets the lock, waits 5 seconds, outputs and calls Thread.yield(); then your second thread gets the lock again and so on.
What you are experiencing is thread starvation. In your case, one thread is being blocked indefinitely waiting to enter a synchronization block because the other thread is constantly allowed access.
To overcome thread starvation you need to employ some sort of fairness locking. Locks that are conceived as fair give priority to the threads waiting the longest to acquire said lock. Such a locking strategy eliminates the possibility of thread starvation and insures all waiting threads will be executed at some time.
Fairness locking in Java can easily be accomplished by using a ReentrantLock with a fairness parameter set to true.
If I have the following dummy code:
public static void main(String[] args) {
TestRunnable test1 = new TestRunnable();
TestRunnable test2 = new TestRunnable();
Thread thread1 = new Thread(test1);
Thread thread2 = new Thread(test2);
thread1.start();
thread2.start();
}
public static class TestRunnable implements Runnable {
#Override
public void run() {
while(true) {
//bla bla
}
}
}
In my current program I have a similar structure i.e. two threads executing the same Run() method. But for some reason only thread 1 is given CPU time i.e. thread 2 never gets a chance to run. Is this because while thread 1 is in its while loop , thread 2 waits?
I'm not exactly sure, if a thread is in a while loop is it "blocking" other threads? I would think so, but not 100% sure so it would be nice to know if anyone could inform me of what actually is happening here.
EDIT
Okay, just tried to make a really simple example again and now both threads are getting CPU time. However this is not the case in my original program. Must be some bug somewhere. Looking into that now. Thanks to everyone for clearing it up, at least I got that knowledge.
There is no guarantee by the JVM that it will halt a busy thread to give other threads some CPU.
It's good practice to call Thread.yield();, or if that doesn't work call Thread.sleep(100);, inside your busy loop to let other threads have some CPU.
At some point a modern operating system will preempt the current context and switch to another thread - however, it will also (being a rather dumb thing overall) turn the CPU into a toaster: this small "busy loop" could be computing a checksum, and it would be a shame to make that run slow!
For this reason, it is often advisable to sleep/yield manually - even sleep(0)1 - which will yield execution of the thread before the OS decides to take control. In practice, for the given empty-loop code, this would result in a change from 99% CPU usage to 0% CPU usage when yielding manually. (Actual figures will vary based on the "work" that is done each loop, etc.)
1The minimum time of yielding a thread/context varies based on OS and configuration which is why it isn't always desirable to yield - but then again Java and "real-time" generally don't go in the same sentence.
The OS is responsible for scheduling the thread. That was changed in couple of years ago. It different between different OS (Windows/Linux etc..) and it depends heavily on the number of CPUs and the code running. If the code does not include some waiting functionality like Thread.yield() or synchhonized block with a wait() method on the monitor, it's likely that the CPU will keep the thread running for a long time.
Having a machine with multiple CPUs will improve your parallelism of your application but it's a bad programming to write a code inside a run() method of a thread that doesn't let other thread to run in a multi-threaded environment.
The actual thread scheduling should be handled by the OS and not Java. This means that each Thread should be given equal running time (although not in a predictable order). In your example, each thread will spin and do nothing while it is active. You can actually see this happening if inside the while loop you do System.out.println(this.toString()). You should see each thread printing itself out while it can.
Why do you think one thread is dominating?