I'm looking to use a thread to process something in the background. Since this code isn't used anywhere else & is not complex I'd like to use an inline function. However the function needs a copy of an attribute at the time the thread was created i.e.: I'd like it if the output from the following example 'true' instead of 'false'
public class InlineThreadTest {
boolean value;
public static void main(String[] args) {
new InlineThreadTest();
}
InlineThreadTest() {
value = true;
java.util.concurrent.Executors.newSingleThreadExecutor().execute(new Runnable() {
#Override
public void run() {
try {
Thread.sleep(100);
} catch (InterruptedException e) {}
System.out.println(value);
}
});
value = false;
}
}
... I can do what I'm looking to do by creating a separate class that implements Runnable, but having this inline seems like something that might be good.
I had a look # https://stackoverflow.com/a/362443/64696 , but cannot figure out how to mold this to my use case.
Runnable implementation is a thread and thread won't return any value. The ExecutorService.execute method just runs the thread and you have no way to get the state of the thread whether it was executed or not.
If you want to check for the task (not thread) executed by ExecutorService you should use Callable and work with sumbit(). Your modified example:
public class InlineThreadTest {
boolean value;
public static void main(String[] args) {
new InlineThreadTest();
}
InlineThreadTest() {
value = true;
java.util.concurrent.Future<Boolean> f =
java.util.concurrent.Executors.newSingleThreadExecutor().submit(new Callable<Boolean>() {
public Boolean call() {
System.out.println(value);
try {
Thread.sleep(100);
} catch (InterruptedException e) {}
value = false;
return value;
}
});
try {
System.out.println(f.get()+" or value="+value);
} catch (Exception ex) { }
}
}
You'll get 2 lines
true
false or value=false
Related
I have two threads. The first changes the value of variable Data. And second one print the value if its value has changed. I am trying to do that second thread just print each time that the variable's value changed, but I don't reach success. Someone can help me?
thread 1
class someservice{
volatile int data;
Boolean Flag = false;
public void mymethod(){
flag = true;
for (Integer i = 1; i < sheet.getRows(); i++) {
data = someMethod(); //this method when called return a new
//value
}
flag = false;
...
}
}
thread 2
Promise p = task {
try {
while (true) {
if (engineService.getFlag()) {
print(someservice.data);
}else{
break;
}
}
} catch(Throwable t) {
...
}
}
Since you mention Promises, I infer you are familiar with future/ promise in +C++11
in java there is a similar approach, with future callable...
public class HW5 {
public static void main(String[] argv) throws InterruptedException, ExecutionException {
FutureTask<Boolean> myFutureTask = new FutureTask<>(new Callable<Boolean>() {
#Override
public Boolean call() throws Exception {
// implement the logic here and return true if everything was
// ok, false otherwise.
Thread.sleep(5000);
System.out.println("dddd");
return System.currentTimeMillis() % 2 == 0;
}
});
ExecutorService executor = Executors.newFixedThreadPool(1);
executor.execute(myFutureTask);
Boolean result = myFutureTask.get();
System.out.println("Done!");
}
}
FutureTask in a class that takes a callable which can return an Object after its job is done... in Order to execute the Future task you can use a Executor service, especifically calling the method execute, since you need to wait for the thread to do the job then is necessary that you call Future.get, that will basically blocks the main thread until the future is done, to verify the result, just read the variable result..
You could use the notify() and notifyAll() methods within thread. Check out this link: https://docs.oracle.com/javase/tutorial/essential/concurrency/guardmeth.html
public synchronized void guardedJoy() {
// This guard only loops once for each special event, which may not
// be the event we're waiting for.
while(!joy) {
try {
wait();
} catch (InterruptedException e) {}
}
System.out.println("Joy and efficiency have been achieved!");
}
public synchronized notifyJoy() {
joy = true;
notifyAll();
}
You have to look up more data about Concurrent programming,I can tell you now some basics,well,not so so basic,but i will do my best:
Here,you have a Monitor,it is an abstract concept,in resume,a Monitor is a
class with all it's
method using"syncronized"
as modifier, it means,
that only
one thread
can access
the method
at once.So,
in the
monitor is
the variable
that you
want to print,
and the"flag",
that tells you if
the variable
was modified.Finally,
you can
see the
most important thing,the"wait()"and"notify()"methods,
those method
stops the thread,or"play"
them again.
You ask
here in
the printValue() method, if your variable was changed, if the variable was'nt change, put the thead to sleep with the wait() method, and when the other
method changeValue() is executed, the value is modified, and the notify() method is called, waking up the thread, so, doing all this, you can guarantee three things:
Safety: meaning that the threads will do that you want
Absence of deadlock: meaning that the thread that is put to sleep, will be awake in the future.
Mutex: meaning that only one thread is executing the critical code, for example, the op. "++" is not atomic, is Subdivided inside in more the one action, create a local var, read the var, sum, and asign, so, if more than one thread are in the game, the value may not be consecutive, example:
i = 0;
i ++;
output: 1;
output: 2;
output: 3;
output: 5;
output: 4;
output: 7;
That could happen, and even so, that will happen in the next code, because there a more than one thread executing. Well, this is the way to program with several threads, more or less
public class Monitor {
private int value = 0;
public static boolean valueHasChanged = false;
public synchronized int changeValue(int newValue){
this.value = newValue;
Monitor.valueHasChanged = true;
this.notify();
return this.value + 1;
}
public synchronized void printValue(){
while(!Monitor.valueHasChanged){
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
System.out.println(this.value);
Monitor.valueHasChanged = false;
}
public static void main(String[] args) {
Monitor ac = new Monitor();
BClass t1 = new BClass(ac);
AClass t2 = new AClass(ac);
t1.start();
t2.start();
}
public int getValue() {
return this.value;
}
}
Now the threads:
public class AClass extends Thread{
private Monitor ac;
public AClass(Monitor ac) {
this.ac = ac;
}
#Override
public void run() {
while(true){
this.ac.printValue();
}
}
}
And finally:
public class BClass extends Thread{
private Monitor ac;
public BClass(Monitor ac) {
this.ac = ac;
}
#Override
public void run() {
int v = 0;
while(true){
this.ac.changeValue(v);
v++; // this sum is not secure, if you want to print an
// ascending order, the code is diferent, I will show in
// above.
}
}
Now, if you want an ordered print:
the monitor will look like:
public class Monitor {
private int value = 0;
public boolean valueHasChanged = false;
private boolean hasPrint = true;
public synchronized void changeValue(int newValue) {
this.value = newValue;
this.valueHasChanged = true;
this.notify();
}
public synchronized void changeValuePlusOne() {
while (!hasPrint) {
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
this.value++;
this.valueHasChanged = true;
this.hasPrint = false;
this.notifyAll();
}
public synchronized void printValue() {
while (!this.valueHasChanged) {
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(this.value);
this.valueHasChanged = false;
this.hasPrint = true;
this.notifyAll();
}
public static void main(String[] args) {
Monitor ac = new Monitor();
BClass t1 = new BClass(ac);
AClass t2 = new AClass(ac);
t1.start();
t2.start();
}
public int getValue() {
return this.value;
}
}
And the Threads:
public class BClass extends Thread{
private Monitor ac;
public BClass(Monitor ac) {
this.ac = ac;
}
#Override
public void run() {
while(true){
this.ac.changeValuePlusOne();
}
}
}
The other Thread look equals:
public class AClass extends Thread{
private Monitor ac;
public AClass(Monitor ac) {
this.ac = ac;
}
#Override
public void run() {
while(true){
this.ac.printValue();
}
}
}
I am making a Java app which does something on a HotKey combination. I have an infinite while loop to wait for HotKey input to close, but it makes the app very CPU time costing.
Following is how my code looks in the simplest way:
static boolean isOpen = true;
void main()
{
....
add SomeHotKeyListener();
....
while(isOpen)
{ }
releaseResources();
}
void onHotKey(int hotKeyIdentifier)
{
if(hotKeyIdentifier == something)
do something;
if(hotKeyIdentifier == something)
isOpen = false;
}
I need a multi-threading approach to achieve this, or if someone has something better to fit in.
I recommend you read about the synchronized keyword in Java. Just Google it, and you should find a ton of examples and tutorials.
This should solve your case:
static boolean isOpen = true;
static Object lock = new Object();
void main()
{
....
add SomeHotKeyListener();
....
synchronized(lock)
{
while(isOpen)
{
try {
lock.wait()
} catch(InterruptedException e) {
}
}
}
releaseResources();
}
void onHotKey(int hotKeyIdentifier)
{
if(hotKeyIdentifier == something)
do something;
if(hotKeyIdentifier == something)
{
synchronized(lock)
{
isOpen = false;
lock.notify();
}
}
}
Infinite while loop can consume quite a lot of system resource. Using wait and notify is recommended. Also you have to declare your boolean volatile as otherwise there is no guarantee that the changes made by one thread is picked up by the other. Below is an example which does something in a separate thread and until interrupted by the calling thread based on a user input (an enter in this case). See also the example from Oracle here
import java.util.Scanner;
public class WaitTest implements Runnable {
private volatile boolean shutdown = false;
public static void main(String[] args) {
WaitTest w = new WaitTest();
new Thread(w).start();
System.out.println("Press any key to interrupt");
Scanner sc = new Scanner(System.in);
sc.nextLine();
w.triggerShutDown();
}
#Override
public void run() {
while (!shutdown) {
synchronized (this) {
try {
System.out.println("doing some silly things");
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
System.out.println("Server shutdown successfully");
}
public synchronized void triggerShutDown() {
this.shutdown = true;
notify();
}
}
I have the following code:
public class Shell {
String status;
Runtime rtime;
Process process;
public void runCmd(final String cmd,String status) throws Exception{
this.status = status;
Thread t = new Thread(new Runnable() {
#Override
public void run() {
try {
process = rtime.exec(cmd);
process.waitFor();
this.status = "check out done";
} catch (IOException e) {
} catch (InterruptedException e) {
}
}
});
t.start();
}
}
but java doesn't let me change the status variable inside the new thread t.May be I need some sort of inter thread communication.I am new to threads,please tell me how to do this.
In your case this in expression this.status refers Runnable object which does not have status field defined. Try Shell.this.status instead of this.status.
The problem is that you cannot access a variable from a parent class in an anonymous class unless it is final and even then it is complex. As you want to modify it I would suggest something like:
public class Holder <T> {
private T held = null;
public Holder () {
}
public Holder (T it) {
held = it;
}
public void hold(T it) {
held = it;
}
public T held() {
return held;
}
#Override
public String toString () {
return held == null ? "null": held.toString();
}
}
Then your code can look like this:
public class Shell {
final Holder<String> status = new Holder<>();
Runtime rtime;
Process process;
public void runCmd(final String cmd, String status) throws Exception {
// Set the status.
Shell.this.status.hold(status);
Thread t = new Thread(new Runnable() {
#Override
public void run() {
try {
process = rtime.exec(cmd);
process.waitFor();
Shell.this.status.hold("check out done");
} catch ( IOException | InterruptedException e) {
}
}
});
t.start();
}
}
Added
This demopnstration of the use of a Holder is the solution to a different problem - i.e. the need to modify a final object from inside an anonymous class.
This answer is not the solution to OP's problem and I would delete it if I could. Unfortunately it has been marked as the answer so I cannot.
If OP could mark one of the other posts as the correct answer I would be happy to delete this.
public class Shell {
volatile String status;
public void runCmd(final String cmd) throws Exception{
Thread t = new Thread(new Runnable() {
#Override
public void run() {
try {
Process process = Runtime.getRuntime().exec(cmd);
process.waitFor();
Shell.this.status = "check out done";
} catch (IOException e) {
} catch (InterruptedException e) {
}
}
});
t.start();
t.join();
System.out.println(status);
}
}
Use Shell.this.status and update the value to what to want.
Thread Safety
Always use volatile when reference is updated from another thread.
Essentially, what I want to do is start all my threads, pause them all, then resume them all, using the multithreading approach. I am just looking for a simple solution to this. I'm not sure if I have to use a timer or what. Right now when I run it, the threads are like being executed in random order (I guess the PC is just randomly picking which ones it wants to run at a certain time).
class ChoppingThread extends Thread
{
public void run()
{
for(int j=40;j!=0;j-=10)
System.out.println("Chopping vegetables...("+j+" seconds left)");
}
}
class MixingThread extends Thread
{
public void run()
{
for(int k=60;k!=0;k-=10)
System.out.println("Mixing sauces...("+k+" seconds left)");
}
}
class TenderizingThread extends Thread
{
public void run()
{
for(int j=50;j!=0;j-=10)
System.out.println("Tenderizing meat...("+j+" seconds left)");
}
}
class MultiThreadTasking
{
public static void main (String [] args)
{
ChoppingThread ct = new ChoppingThread();
MixingThread mt = new MixingThread();
TenderizingThread tt = new TenderizingThread();
System.out.println("\nWelcome to the busy kitchen.");
//putting threads into ready state
ct.start();
mt.start();
tt.start();
}
}
There are probably other ways to achieve the same result, but this is the simplest I can come up with off the top of my head (I know, sad isn't it)...
Basically, this is a special Runnable with some additional management functionality.
This basically contains a state flag that indicates the state of the task and a monitor lock
public class ThreadFun {
public static void main(String[] args) {
MyTask task = new MyTask();
Thread thread = new Thread(task);
thread.start();
try {
Thread.sleep(1000);
} catch (InterruptedException ex) {
}
task.pauseTask();
try {
Thread.sleep(1000);
} catch (InterruptedException ex) {
}
task.resumeTask();
try {
Thread.sleep(1000);
} catch (InterruptedException ex) {
}
task.stopTask();
}
public enum TaskState {
Running,
Stopped,
Paused
}
public static class MyTask implements Runnable {
private static final Object PAUSED_LOCK = new Object();
private volatile TaskState state = TaskState.Running;
public void pauseTask() {
if (state == TaskState.Running) {
System.out.println("Paused...");
state = TaskState.Paused;
}
}
public void resumeTask() {
if (state == TaskState.Paused) {
state = TaskState.Running;
synchronized (PAUSED_LOCK) {
PAUSED_LOCK.notifyAll();
}
System.out.println("Resumed...");
}
}
public void stopTask() {
if (state == TaskState.Running || state == TaskState.Paused) {
state = TaskState.Stopped;
System.out.println("Stopped...");
}
}
public boolean isStopped() {
return state == TaskState.Stopped;
}
public boolean isPaused() {
return state == TaskState.Paused;
}
protected void doPause() {
synchronized (PAUSED_LOCK) {
while (isPaused()) {
try {
PAUSED_LOCK.wait();
} catch (InterruptedException ex) {
}
}
}
}
#Override
public void run() {
int index = 0;
while (!isStopped() && index < 1000) {
try {
Thread.sleep(25);
} catch (InterruptedException ex) {
}
doPause();
index++;
System.out.println(index);
}
stopTask(); // Make sure the task is marked as begin stopped ;)
}
}
}
The main criteria is you will need to pool isStopped and doPause at appropriate points to ensure that they are begin implemented as required...
To coordinate them use a CyclicBarrier.
To launch them all at the same time use a CountDownLatch.
Google the two classes above for many examples and explanations.
To fully understand what is happening read the Java Concurrency In Practice book.
I believe you can accomplish this by using Object.wait and Thread.interrupt.
Object.wait blocks until notify is called. So
private boolean paused;
private Object waitObject;
...
public void run() {
for ... {
if (this.paused) { this.waitObject.wait(); }
...
public void pause() { this.paused = true; }
public void resume() { this.paused = false; this.waitObject.notify(); }
Then you can call pause to pause the thread.
Thread.interrupt can help with stopping.
private boolean paused;
...
public void run() {
for ... {
// interrupted() is different from interrupt()!
if (this.iterrupted()) { break; }
...
To stop it, you would call interrupt() from another thread.
This is the basic idea, but there's a lot of details to worry about here. For example, wait can throw an InterruptedException you'll need to handle. Also, wait is not guaranteed to return only after a notify. It can return randomly. Here is a pair of tutorials:
Wait: http://docs.oracle.com/javase/tutorial/essential/concurrency/guardmeth.html
Interrupt: http://docs.oracle.com/javase/tutorial/essential/concurrency/interrupt.html
Code snippet:
class Counter implements Runnable {
Object s = new Object();
#Override
public void run() {
try {
synchronized (s) {
s.wait(10000);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
//...do Something
}
public void stopCounter() {
synchronized (s) {
s.notifyAll();
}
}
}
Irrespective of whether i call stopCounter or not, the ...do Something code always executes only after the wait interval. Even after notify it still waits for 10 secs.
I cannot tell from your example what you are trying to achieve. If it is to try and replace some sort of polling then consider the BlockingQueue interface that was released in Java 5. Since that has appeared I have had no need for wait/notify. It's a lot more simple to use and java behind the scenes does the equivalent of the wait/notify for you.
It depends of the way you use it. I have just tried it by adding a main method and running it and it seems like the wait / notify mechanism is working fine, not the way you described it. Please try it yourself:
public static void main(String[] args) {
Counter c = new Counter();
new Thread(c).start();
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
c.stopCounter();
}
My guess is that you call the run and stopCounter methods on different instances of your Counter class. They therefore use different monitors (your s = new Object()) and the call to stop won't notify the other Counter.
For example, this would behave similarly to what you describe (unless you get a spurious wakeup):
public static void main(String[] args) throws InterruptedException {
Counter c = new Counter();
new Thread(c).start();
Thread.sleep(200);
new Counter().stopCounter();
}
static class Counter implements Runnable {
Object s = new Object();
#Override
public void run() {
try {
System.out.println("in");
synchronized (s) {
s.wait(10000);
}
System.out.println("out");
} catch (InterruptedException e) {
e.printStackTrace();
}
//...do Something
}
public void stopCounter() {
synchronized (s) {
s.notifyAll();
}
System.out.println("notified");
}
}