This question already has answers here:
Program hangs if thread is created in static initializer block
(4 answers)
Closed 8 years ago.
Can someone explain to me why the following code prints nothing?
When I tried to debug it, the debugger froze on the line t.join();. But in the debugger I saw the message: "program is running".
public class Main_problem1_multithreading {
private static boolean initialized = false;
static {
Thread t = new Thread(new Runnable() {
#Override
public void run() {
initialized = true;
}
});
t.start();
try {
t.join();
} catch (InterruptedException e) {
throw new AssertionError(e);
}
}
public static void main(String[] args) {
System.out.println(initialized);
}
}
Static initialization takes place when JVM loads a class first time. The thread that loads the class has a lock on Static Initializer , In this case main thread is already holding the lock.
Until that lock is released the newly spawned thread cannot access "initialized" variable.
You can clearly see in the image I attached. Thread - 0 is stepping at line 10. Line 10 is where new thread tries to update initialized variable. So this new thread keep waiting for the lock which it never gets and main thread keeps waiting for new thread to join it. Deadlock!! Hope it helps!
package com.test;
public class Test {
private static boolean initialized = false;
static {
Thread t = new Thread(new Runnable() {
#Override
public void run() {
initialized = true;
System.out.println("New Thread" + initialized);
}
});
t.start();
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
System.out.println("Main Thread" + initialized);
}
}
Related
This question already has answers here:
Java Wait and Notify: IllegalMonitorStateException
(2 answers)
Closed 4 years ago.
Was trying to practice producer and consumer using a simple counter in java.
Not sure why I am getting a Illegal Monitor State exception on this piece of code.
I have counter rest and counter consume methods which run in their own thread.
The counter itself is a static int volatile field .
The counter class also gives you a lock to
If I change the wait naotify to the following:
Counter.lock.notify();
Counter.lock.wait();
The code works. Dosen't wait() and notify() automatically takes the reference of the lock synchronize is on?
Producer Class
package multithreading;
public class CounterProducer implements Runnable {
public void run() {
try { incrCounter(); } catch (InterruptedException e) { e.printStackTrace(); }
}
public void incrCounter() throws InterruptedException {
while (true) {
synchronized (Counter.lock) {
if (Counter.counter < 1) {
System.out.println("Counter Reset");
Counter.counter = 10;
notify();
wait();
}
}
}
}
}
Consumer Class
package multithreading;
public class CounterConsumer implements Runnable {
public void run() {
try { consumeCounter(); } catch (InterruptedException e) { e.printStackTrace(); }
}
public void consumeCounter() throws InterruptedException {
while (true) {
synchronized (Counter.lock) {
if (Counter.counter > 0) {
System.out.println("Consumed");
Counter.counter--;
notify();
wait();
}
}
}
}
}
The Counter
public class Counter {
public static volatile int counter;
public static final Object lock = new Object();
}
The Counter
public class CounterRunner {
public static void main(String[] args) {
Thread con = new Thread(new CounterConsumer());
Thread prod = new Thread(new CounterProducer());
con.start();
prod.start();
}
}
The Runner
public class CounterRunner {
public static void main(String[] args) {
Thread con = new Thread(new CounterConsumer());
Thread prod = new Thread(new CounterProducer());
con.start();
prod.start();
}
}
If I change the wait naotify to the following, the code works:
Counter.lock.notify();
Counter.lock.wait();
Every Java method is either a static method of some class or an instance method of some object. If you see a method call that does not contain an explicit class name or object reference, then it is an implicit call to a method belonging to the this object.
That is to say, notify() means the same thing as this.notify(), and wait() means this.wait().
this, refers to the CounterProducer instance when it appears in your CounterProducer.incrCounter() method, and it refers to the CounterConsumer instance when it appears in your CounterConsumer.consumeCounter() method.
This question already has answers here:
Program hangs if thread is created in static initializer block
(4 answers)
Closed 6 years ago.
This class does not initialize itself in the usual way, so it calls on the help of background thread.
From my understanding ,surely the program must print true ?
But If you ran the program, you found that it prints nothing; it just hangs.
public class Test {
private static boolean isInitialized = false;
static {
Thread t = new Thread(new Runnable() {
public void run() {
isInitialized = true;
}
});
t.start();
try {
t.join();
} catch (InterruptedException e) {
}
}
public static void main(String[] args) {
System.out.println(isInitialized);
}
}
Can some one please explain why this is happening.
"The static initializer for a class gets run when the class is first accessed, either to create an instance, or to access a static method or field." Static Initialization Blocks
I guess that this program to start needs to first initialize the class Test. And so it tries first to execute static block but that block never exits (since it cannot set static member isInitialized as it is not ready yet).
So Test class is never fully initialized and therefore main method is not even starting to be executed.
The solution for you could be moving the instruction of waiting for your initialization thread to finish - to the main method. So it does not block the Test class from being fully initailzed.
package com.company;
public class Test {
private static boolean isInitialized = false;
static Thread t = new Thread(new Runnable() {
public void run() {
isInitialized = true;
}
});
static {
t.start();
}
public static void main(String[] args) {
try {
t.join();
} catch (InterruptedException ignored) { }
System.out.println(isInitialized);
}
}
While doing some practices on multi-threading, I found that I can not set the name of the thread in my code. I can use this to refer the current object then why I can not use Thread.currentThread while constructing thread to access current thread. I am bit confusing. please help me.
When actually thread creating? Is it when constructing thread instance or while calling method start() on thread?
what is currentThread means here?
public class RecursiveRunnableTest {
public static void main(String... args){
Thread t = new Thread(new RecursiveRunnable("First thread"));
t.start();
}
}
class RecursiveRunnable implements Runnable {
private String name;
public RecursiveRunnable(String name) {
this.name = name;
Thread.currentThread().setName(this.name); // Expecting to set the name of thread here
}
#Override
public synchronized void run() {
System.out.println(Thread.currentThread().getName()); // displaying Thread-0
System.out.println(this.name); // displaying "First thread"
try{
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}finally{
}
}
}
Simply because main thread constructs it not the t thread constructs itself. So, you may rewrite to this one (setting thread's name before starting it):
public class RecursiveRunnableTest {
public static void main(String... args){
RecursiveRunnable rr = new RecursiveRunnable("First thread");
Thread t = new Thread(rr);
t.setName(rr.getName());
t.start();
}
}
class RecursiveRunnable implements Runnable{
private String name;
public RecursiveRunnable(String name) {
this.name = name;
}
public String getName(){return this.name;}
#Override
public synchronized void run() {
System.out.println(Thread.currentThread().getName()); // displaying Thread-0
System.out.println(this.name); // displaying "First thread"
try{
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}finally{
}
}
}
Try doing this instead
Thread t = new Thread(new RecursiveRunnable("First thread"));
t.start();
Thread.sleep(1L);
System.out.println("main thread: " + Thread.currentThread().getName()); // same thread that created the RecrusiveRunnable instance
you will see
main thread: First thread
printed.
This is because the main thread builds the RecursiveRunnable, so
Thread.currentThread().setName(this.name);
is actually changing the name of the main thread, not the thread that the Runnable will eventually run in.
Also
System.out.println(this.name); // displaying "First thread"
is referring to the name field of the RecursiveRunnable object, which you've set to the same value as the main thread.
I have some problem with java.
for Example,
public class Test implements Runnable{
Thread thread;
public Test() throws Exception{
thread = new Thread(this);
thread.setName(getClass().getName() + thread.getId());
thread.start();
}
public void run() {
System.out.println("start");
try {
while(!thread.isInterrupted())
Thread.sleep(Long.MAX_VALUE);
}
catch(InterruptedException ie) {
System.out.println("interrupted");
}
System.out.println("stop");
}
public void stop() {
thread.interrupt();
}
}
this code now is infinite sleep status.
then, I find this thread by name in another Java code (something like this way - http://www.ehow.com/how_7467934_java-thread-runtime.html)
I casted "found thread" to Test class
Test test = (Test)Found Thread;
finally,
test.stop();
work!
I want to find and stop this thread in the other application (absolutely not same)
I`m not familiar with Java, also this like code way will not work in C++ or others as I know.
Is my code in sense? no problem? I worry about...
please advise me. thanx a lot.
(I`m not good at english. sorry)
There is no problem in your code! Everything is just perfect. You may omit checking interrupted status of thread in sleep loop, because once thread is interrupted, it will going to throw that exception when it tries to sleep or wait.
public class Test implements Runnable {
Thread thread;
public Test() throws Exception {
thread = new Thread(this);
thread.setName(getClass().getName() + thread.getId());
thread.start();
}
public void run() {
System.out.println("start");
try {
while (true) {
Thread.sleep(Long.MAX_VALUE);
}
} catch (InterruptedException ie) {
System.out.println("interrupted");
}
System.out.println("stop");
}
public void stop() {
thread.interrupt();
}
public static void main(String [] args) throws Exception{
Test t = new Test();
t.stop();
}
}
I can't figure out what is the problem in the following code:
I have a thread that can be suspended and resumed
Code bellow:
public class CustomThread implements Runnable {
private volatile boolean stop;
private volatile boolean suspend;
String[] names = new String[]{
"A", "B","C","D","E", "F", "G","H","I","J","K", "L"
};
public CustomThread(){
Collections.shuffle(Arrays.asList(names));
System.out.println("Available names:");
System.out.println(Arrays.asList(names));
}
#Override
public void run() {
while(!stop){
synchronized (this) {
if(suspend){
try {
System.out.println("Got suspended");
wait();
System.out.println("Resumed");
} catch (InterruptedException e) {
System.out.println("Got interupted");
}
}
else System.out.println("Suspend false");
}
int randomIdx = new Random().nextInt(names.length);
System.out.println(names[randomIdx]);
}
}
public synchronized void suspend(){
System.out.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>Suspend true");
suspend = true;
}
public synchronized void resume(){
suspend = false;
notify();
}
}
I run the following simple code:
public class CustomTest {
/**
* #param args
* #throws InterruptedException
*/
public static void main(String[] args) throws InterruptedException {
CustomThread c = new CustomThread();
Thread t = new Thread(c);
t.start();
Thread.sleep(5000);
System.out.println("++++++++++++++++++++++++++++++++");
c.suspend();
}
}
What I am expecting to see is:
Thread custom runs, main sleeps, main suspends the custom thread by c.suspend() and since main terminates and noone resumes the thread, the thread remains in wait state.
But what I see instead is that the CustomThread prints continually Suspend false and an element from names.
What is the problem here? It is like the Thread.sleep(5000) and c.suspend() in main don't do anything.
The code is fine as written, but your problem is probably that you are running this through Eclipse and you are overwhelming the console. Put a shorter delay in main and you'll see good results.
Note: your suspend method doesn't need to be synchronized as it only writes to a volatile variable.
Instead of if(suspend) you should have while(suspend), see the explanation in javadoc here: http://docs.oracle.com/javase/6/docs/api/java/lang/Object.html#wait%28%29
From the javadoc of Object.wait():
...interrupts and spurious wakeups are
possible, and this method should always be used in a loop