| | |
Threads - need little help
Thread Solved |
I yet did not master the skill of concurrency better say I failed on first attempt and since then did not tried, therefore I'm asking for help. Currently I working on JME application where I need to load mp3 files into Player. I'm able to do it with one file, however I'm failing to start playing next one after previous finished. I tried to use Threads but the run() method never get executed.
Basically somewhere in my application I will call method optionSelected(String). The method will start first thread and is supposed to wait till thread ends to start next thread with upload of next mp3 file and play it.
For unknown reason to me the run() method never get executed and application continue with other business.
Basically somewhere in my application I will call method optionSelected(String). The method will start first thread and is supposed to wait till thread ends to start next thread with upload of next mp3 file and play it.
Java Syntax (Toggle Plain Text)
public void optionSelected(String str) { t = new Thread("SEL"); t.start(); soundURL ="/sesimulator/res/"+str+".mp3"; t = new Thread("soundURL"); t.start(); }
Learn to see in another's calamity the ills which you should avoid.
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
I don't think it's the run method that isn't executing, Peter.
I think the problem is that you are not submitting a Runnable target as the argument for the Thread to execute.
I actually don't understand why the Thread class is not abstract if it allows one to simply give a Thread a title, but I will investigate this a bit more thoroughly and help you find a conclusion.
I think the problem is that you are not submitting a Runnable target as the argument for the Thread to execute.
I actually don't understand why the Thread class is not abstract if it allows one to simply give a Thread a title, but I will investigate this a bit more thoroughly and help you find a conclusion.
Yes, the Threads in your example don't really do anything. You need to extend Thread and override run() or supply a Runnable to the constructor. Have you looked through the tutorial on concurrency as a starting point?
http://java.sun.com/docs/books/tutor...runthread.html
The java.util.concurrent package adds a lot of new higher level support structure for asynchronous operations as well. It's covered further towards the end of the tutorial trail.
http://java.sun.com/docs/books/tutor...runthread.html
The java.util.concurrent package adds a lot of new higher level support structure for asynchronous operations as well. It's covered further towards the end of the tutorial trail.
Just to answer the question on waiting for one thread to finish before starting the next, here's a trivial example using the join() method
java Syntax (Toggle Plain Text)
public class JoinExample { public static void main(String args[]) { Thread t1 = new Thread(new FirstTask()); Thread t2 = new Thread(new SecondTask()); t1.start(); try { // wait for t1 to complete t1.join(); } catch (InterruptedException ex) { Thread.currentThread().interrupt(); } // start the next t2.start(); } static class FirstTask implements Runnable { int counter=0; public void run() { try { while (counter<10){ System.out.println(++counter); Thread.sleep(500); } } catch (InterruptedException e) { Thread.currentThread().interrupt(); } } } static class SecondTask implements Runnable { int counter=64; public void run() { try { while (counter<74){ System.out.println(Character.toChars(++counter)); Thread.sleep(1000); } } catch (InterruptedException e) { Thread.currentThread().interrupt(); } } } }
Last edited by Ezzaral; Sep 16th, 2008 at 6:24 pm.
Here's yet another example, though probably overkill--
java Syntax (Toggle Plain Text)
import java.util.concurrent.*; import java.net.*; public class ConcurrentExample{ public final ExecutorService es; private Future currentFuture = null; public ConcurrentExample(){ es = Executors.newFixedThreadPool(1); } public static void main(String... args){ ConcurrentExample ce = new ConcurrentExample(); ce.optionSelected("http://www.google.com"); // invokes the run method - main process takes 5 seconds ConcurrentExample.advance(4, false); // silently wait 4 seconds before performing new task ce.optionSelected("http://www.yahoo.com"); // this request should fail since current request is still occurring ConcurrentExample.advance(6, false); // silently wait 6 seconds before performing new task ce.optionSelected("http://www.msn.com"); // this request should succeed since the previous task should have finished ce.es.shutdownNow(); // shut down processes so the JVM can exit naturally. } public static void advance(int seconds, boolean displayStatus){ long first = System.currentTimeMillis(); // get current time long second = (seconds * 1000) + first; // get time arg seconds ahead of the first int count = 0; // while the first time is not equal to the second, assign first to the current time while(first < second){ if((second - first) == 1000 && displayStatus){ System.out.println( "Second: " + (++count)); } first = System.currentTimeMillis(); } } private class Error242 extends Exception{ public Error242(String arg){ super(arg); } public Error242(){ super("An error occurred with the specified request!\nPlease try again!"); } } public void optionSelected(String str){ // A new thread should only execute after the previous is finished-- if(currentFuture == null){ try{ currentFuture = es.submit(new Request(str)); }catch(Exception e){ System.out.println(e); } }else System.out.println("There is currently a task in process... please wait."); /* t = new Thread("SEL"); // assuming a seperate repetitive process t.start(); // starting that process soundURL ="/sesimulator/res/"+str+".mp3"; // process specified by user t = new Thread("soundURL"); // assign request t.start(); // start request */ } /* // Probably not needed-- private Runnable rt = new Runnable(){ @Override public void run(){ // task specific to "SEL" } }; */ private class Request implements Runnable{ private URL userRequest = null; public Request(String userURL) throws Error242{ try{ userRequest = new URL(userURL); }catch(MalformedURLException me){ // send error to some log for statistical reasons... throw new Error242(); // a more user-friendly error } } @Override public void run(){ // task specific to SEL // task to be performed based on the user's request // dummy task to test the logic-- ConcurrentExample.advance(5, true); // loudly wait 5 seconds // finally set the currentFuture to be null when the process is finished-- currentFuture = null; } } }
Last edited by Alex Edwards; Sep 16th, 2008 at 6:52 pm.
Thanx guys, I will play around with these examples. Already see few of the mistakes. Sorry that I can not provide more details as it is MSc project and I do not want to get my back side nailed for plagiarism (not now for sure) .
Can you suggest some easy reading on concurrency (I like reading in style of Deitel or OReilly books, explanation with plenty of examples to try out)? My teacher was useless, about 3/4 of the class failed module, it was university record that may not ever be challenged
Can you suggest some easy reading on concurrency (I like reading in style of Deitel or OReilly books, explanation with plenty of examples to try out)? My teacher was useless, about 3/4 of the class failed module, it was university record that may not ever be challenged
Learn to see in another's calamity the ills which you should avoid.
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
Sometimes the best way to test to see if something is concurrent or not is to use a tracing technique.
Basically split the code that is shared by threads onto different pieces of paper and pretend that one each paper resembles a Thread attempting to access or perform an operation.
If two threads enter the same function, is the function Thread safe? Are you accessing a reference of one object between two threads? Are you doing initialization that may not be thread safe (basically, both Threads may pass a particular condition test and cause something to be initialized twice) ?
The above code I provided is actually not thread safe, now that I think about it. If two threads are accessing the optionSelected(String) method and they are nearly as fast as each other, then there may be 2 requests to submit 2 different threads, however in this case it's even worse because the ExecutorService is initialized with 1 reusable Thread which means the other request may or may not be tossed aside. Even if it is tossed aside, it's still poor programming practice to simply leave it up to objects to handle errors that they were not defined to handle.
In this event I'd use a Double-Checked lock, so that when the method is called the first time it is synchronized upon a lock object and initialized properly. Afterward, there should be no cost of synchronization when a Thread is already doing its job.
An example--
-- you could also lock upon the actual class that is being used by using synchronized(this), though I'm not entirely sure if this is recommended (for example, if an enclosing class of this class is using threads that lock on this object, does that mean there is extra indirection between threads monitoring the state of this object?). In addition, you can lock upon Singletons (or more generally, static instances) by using the qualified name with the .class extension.
Above I mention the volatile keyword, though I'm still not entirely sure I understand the concept of it between Java and C/C++. In C++ it is used as a signal the compiler that a particular chunk of code that performs operations on a particular member should not be optimized into a constant expression (which, I believe has more significance in Device Driver work). In Java, I believe it is used to determine if a particular instance/variable has been initialized properly (between Threads), though again I'm not 100% sure as the use of volatile is very elusive and very specialized.
Edit: Although the static function advance may not be considered Thread safe (due to the fact that multiple threads are accessing a potentially unsynchronized method of class System, and the fact that no threads are locking upon System.class), the members created from calling the function, and the intent of getting the current time of the system makes the function 'synchronized enough.' If you wanted to be completely correct, you'd have to lock on the System class which may not be preferable and may cause an IllegalMonitorState exception if you attempted to use System variables when a Thread has the lock on the System object.
Basically split the code that is shared by threads onto different pieces of paper and pretend that one each paper resembles a Thread attempting to access or perform an operation.
If two threads enter the same function, is the function Thread safe? Are you accessing a reference of one object between two threads? Are you doing initialization that may not be thread safe (basically, both Threads may pass a particular condition test and cause something to be initialized twice) ?
The above code I provided is actually not thread safe, now that I think about it. If two threads are accessing the optionSelected(String) method and they are nearly as fast as each other, then there may be 2 requests to submit 2 different threads, however in this case it's even worse because the ExecutorService is initialized with 1 reusable Thread which means the other request may or may not be tossed aside. Even if it is tossed aside, it's still poor programming practice to simply leave it up to objects to handle errors that they were not defined to handle.
In this event I'd use a Double-Checked lock, so that when the method is called the first time it is synchronized upon a lock object and initialized properly. Afterward, there should be no cost of synchronization when a Thread is already doing its job.
An example--
java Syntax (Toggle Plain Text)
import java.util.concurrent.*; import java.net.*; public class ConcurrentExample{ public final ExecutorService es; private volatile Future currentFuture = null; // if multiple threads share access to changing reference, // then [merely guessing] they need to be able to notice changes done to // shared reference. private Object lockObject = new Object(); public ConcurrentExample(){ es = Executors.newFixedThreadPool(1); } public static void main(String... args){ ConcurrentExample ce = new ConcurrentExample(); ce.optionSelected("http://www.google.com"); // invokes the run method - main process takes 5 seconds ConcurrentExample.advance(4, false); // silently wait 4 seconds before performing new task ce.optionSelected("http://www.yahoo.com"); // this request should fail since current request is still occurring ConcurrentExample.advance(6, false); // silently wait 6 seconds before performing new task ce.optionSelected("http://www.msn.com"); // this request should succeed since the previous task should have finished ce.es.shutdownNow(); // shut down processes so the JVM can exit naturally. } public static void advance(int seconds, boolean displayStatus){ long first = System.currentTimeMillis(); // get current time long second = (seconds * 1000) + first; // get time 10 seconds ahead of the first int count = 0; // while the first time is not equal to the second, assign first to the current time while(first < second){ if((second - first) == 1000 && displayStatus){ System.out.println( "Second: " + (++count)); } first = System.currentTimeMillis(); } } private class Error242 extends Exception{ public Error242(String arg){ super(arg); } public Error242(){ super("An error occurred with the specified request!\nPlease try again!"); } } public void optionSelected(String str){ // A new thread should only execute after the previous is finished-- if(currentFuture == null){ // first test, but not thread safe - when it isn't null threads will skip this synchronized(lockObject){ // locks all threads, but one, out of the statement if(currentFuture == null){ // the single thread checks to see if currentFuture is null try{ currentFuture = es.submit(new Request(str)); // single thread attempts this task }catch(Exception e){ System.out.println(e); } } } // single thread has exited statement, releasing the lock and allowing a different thread to enter }else System.out.println("There is currently a task in process... please wait."); } private class Request implements Runnable{ private URL userRequest = null; public Request(String userURL) throws Error242{ try{ userRequest = new URL(userURL); }catch(MalformedURLException me){ // send error to some log for statistical reasons... throw new Error242(); // a more user-friendly error } } @Override public void run(){ // task specific to SEL // task to be performed based on the user's request // dummy task to test the logic-- ConcurrentExample.advance(5, true); // loudly wait 5 seconds // finally set the currentFuture to be null when the process is finished-- currentFuture = null; } } }
-- you could also lock upon the actual class that is being used by using synchronized(this), though I'm not entirely sure if this is recommended (for example, if an enclosing class of this class is using threads that lock on this object, does that mean there is extra indirection between threads monitoring the state of this object?). In addition, you can lock upon Singletons (or more generally, static instances) by using the qualified name with the .class extension.
Above I mention the volatile keyword, though I'm still not entirely sure I understand the concept of it between Java and C/C++. In C++ it is used as a signal the compiler that a particular chunk of code that performs operations on a particular member should not be optimized into a constant expression (which, I believe has more significance in Device Driver work). In Java, I believe it is used to determine if a particular instance/variable has been initialized properly (between Threads), though again I'm not 100% sure as the use of volatile is very elusive and very specialized.
Edit: Although the static function advance may not be considered Thread safe (due to the fact that multiple threads are accessing a potentially unsynchronized method of class System, and the fact that no threads are locking upon System.class), the members created from calling the function, and the intent of getting the current time of the system makes the function 'synchronized enough.' If you wanted to be completely correct, you'd have to lock on the System class which may not be preferable and may cause an IllegalMonitorState exception if you attempted to use System variables when a Thread has the lock on the System object.
Last edited by Alex Edwards; Sep 16th, 2008 at 10:59 pm.
•
•
•
•
Can you suggest some easy reading on concurrency (I like reading in style of Deitel or OReilly books, explanation with plenty of examples to try out)
Last edited by stephen84s; Sep 17th, 2008 at 2:59 am.
"Any fool can write code that a computer can understand. Good programmers write code that humans can understand."
"How to ask questions the smart way ?"
"How to ask questions the smart way ?"
OK guys, it is working!
Current state of JSR-135: Mobile Media API still need lot of work. The main problem was I couldn't get PlayerListener working correctly to tell me when the song ends with (Player.END_OF_MEDIA) so I could supply another InputStream at that point to play.
Therefore I started to play around with threads and come to ask for help. I went ahead with Ezzaral solution and implemented into my application, however it was still giving me same result (little of first file over played by second). On the end I decided to read duration of song (Player.getDuration()) which returns long. However this long is not compatible with time in milliseconds. By pure luck I tried to divide by thousand and it seems to return correct number to use with Thread.sleep() method.
Looking at current state I think whole threads structure is not necessary and sleep method can handle all
.
Thank you for your time and help, I really appropriate it.
Current state of JSR-135: Mobile Media API still need lot of work. The main problem was I couldn't get PlayerListener working correctly to tell me when the song ends with (Player.END_OF_MEDIA) so I could supply another InputStream at that point to play.
Therefore I started to play around with threads and come to ask for help. I went ahead with Ezzaral solution and implemented into my application, however it was still giving me same result (little of first file over played by second). On the end I decided to read duration of song (Player.getDuration()) which returns long. However this long is not compatible with time in milliseconds. By pure luck I tried to divide by thousand and it seems to return correct number to use with Thread.sleep() method.
Looking at current state I think whole threads structure is not necessary and sleep method can handle all
.Thank you for your time and help, I really appropriate it.
Learn to see in another's calamity the ills which you should avoid.
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
Publilius Syrus
(~100 BC)
LJC - London Java Community, Graduate & Undergraduate Software Development Community, JAVAWUG (Java Web User Group), The London Android Group
![]() |
Similar Threads
- I want google to index forum threads (Search Engine Optimization)
- new way the threads are timed (DaniWeb Community Feedback)
- IE won't let me access threads. Could someone email me a solution please? (Web Browsers)
Other Threads in the Java Forum
- Previous Thread: Please check if this compiles in Windows.
- Next Thread: Please with homework...did alot of work already and I'm stuck
| Thread Tools | Search this Thread |
account android api applet application array arrays automation bidirectional binary birt bluetooth class classes client code columns component constructor database designadrawingapplicationusingjavajslider draw eclipse error errors exception expand fractal game givemetehcodez graphics gui guidancer homework html ide image inetaddress inheritance integer intellij j2me java javamicroeditionuseofmotionsensor javaprojects jlabel jme jni jpanel jtextfield jtree julia linux list loop map method methods midlethttpconnection mobile mobiledevelopmentcreatejar monitoring myaggfun netbeans newbie nullpointerexception open-source oracle plazmic print problem program project property recursion ria scanner search server set sharepoint smart sms smsspam sort sourcelabs splash sql sqlite static string subclass support swing testautomation threads tree unlimited webservices windows






