0

In java, what are the suggested ways to implement the two thread requirements

  1. I would like the name a thread
  2. I would like the parent (or main) thread know if there are any exceptions by this child thread.

For 2, I understand that having a future object would be a better approach. So to implement the above two requirements below is a code I came up with

class MyRunnable implements Runnable {
  ....
}


MyRunnable myRunnable = new MyRunnable ();
FutureTask futureTask = new FutureTask(myRunnable, null);
Thread myThread = new MyThread(futureTask, "processing-thread");
myThread.start();
try {
   futureTask.get();
} catch (Exception e) {
   throw new RuntimeException(e)
}

This seems to be a lot of code for simple stuff. Any better ways?

Note - Using executorService is not an option since I have threads which are not doing similar tasks. Also executorService accepts a thread name prefix instead of a thread name. I want to give each thread a unique name.

Community
  • 1
  • 1
Andy Dufresne
  • 6,022
  • 7
  • 63
  • 113
  • Look up [ThreadFactory](http://docs.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/ThreadFactory.html). Implementing one, you can have unique naming for each new Thread you request from it. You can also provide one to an ExecutorService and thus override its naming. What makes you think an ExecutorService requires the tasks to be similar? – Fildor Jun 05 '13 at 06:22
  • @Fildor - Thanks for the reply. How do I use a ThreadFactory without using a ExecutorService? Btw I thought that since ExecutorService names threads with a convention like "pool-1-thread-1" by default it is for submitting similar executing tasks. How do I submit different threads and give unique names to them using a ExecutorService? – Andy Dufresne Jun 05 '13 at 06:45

2 Answers2

2

Using executorService is not an option since I have threads which are not doing similar tasks.

I don't see how this would matter.

Also executorService accepts a thread name prefix instead of a thread name. I want to give each thread a unique name.

So give each thread a name with a ThreadFactory. I have a class which I call a NamedThreadFactory.

I suspect what you would like the thread to do is reflect what the task is doing.

You can do this

ExecutorService es = Executors.newSingleThreadExecutor();
es.submit(new Runnable() {
    public void run() {
        Thread.currentThread().setName("Working on task A");
        try {
            System.out.println("Running: "+Thread.currentThread());
        } finally {
            Thread.currentThread().setName("parked worker thread");
        }
    }
});
es.shutdown();

prints

Running: Thread[Working on task A,5,main]

BTW There is no point starting a thread and immediately waiting for it to finish. You may as well use the current thread.

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
  • executorService names the threads by its own convention if a thread factory instance is not passed. So calling Thread.currentThread().setName("my-name") wont work, I guess. – Andy Dufresne Jun 05 '13 at 06:46
  • @AndyDufresne Or you could try it, see my updated answer. I am third for Java in terms of reputation, and the first to get a silver badge for the JVM ;) – Peter Lawrey Jun 05 '13 at 06:48
  • Ok. My mistake. It works. Btw, isn't it not clean to use a executorservice for executing tasks which do not have anything common or are not similar? – Andy Dufresne Jun 05 '13 at 10:41
  • @AndyDufresne I would have said the ExecutorService is design to execute random Runnables and Callables which may not have anything to do with one another. It designed to aggregate work which might have been done by more threads into smaller threads pools. – Peter Lawrey Jun 07 '13 at 05:32
0

For the naming:

ThreadFactory myFactory = new ThreadFactory(){
  @Override public Thread newThread( Runnable r ) {
       return new Thread( r, getName() )
  }

  private int number = 0;

  private String getName(){
      return "MyThread_" + (number++);
  }

}

There are other ways, too. This is the I like best, personnally.

---EDIT---

To give the thread completely different names, I would go another way:

One possibility would be to set the name inside the Runnable: See Peter's answer with one addition: instead of the fixed String, you could initialize a member variable of your Runnable implementation before starting the Thread.

Fildor
  • 14,510
  • 4
  • 35
  • 67
  • Please see my edit. Using a ThreadFactory without Executor is easy: Instead of `new Thread(...` you call `myThreadFactory.newThread( myRunnable)`. – Fildor Jun 05 '13 at 07:05