Name: nt126004 Date: 08/21/2001
java version "1.3.0"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.3.0-C)
Java HotSpot(TM) Client VM (build 1.3.0-C, mixed mode)
I use ThreadGroup.activeCount() to get the number of active threads.
Then use ThreadGroup.enumerate(Thread[]) to copy all active threads into Thread
[] , but i find that ThreadGroup.enumerate(Thread[]) only copy the first thread
into Thread[]. The result of activeCount() is always 2, however enumerate only
finds one Thread.
please see the source code (from Thinking in JAVA by Bruce Eckel) and the
result below:
=====================
//:TestAccess.java
//How threads can access other threads
//in a parent thread group
public class TestAccess {
public static void main(String[] args){
ThreadGroup
x =new ThreadGroup("x"),
y =new ThreadGroup(x,"y"),
z =new ThreadGroup(y,"z");
Thread
one =new TestThread1(x,"one"),
two =new TestThread2(z,"two");
}
}
class TestThread1 extends Thread {
private int i;
TestThread1(ThreadGroup g,String name){
super(g,name);
}
void f(){
i++; //modify this thread
System.out.println(getName()+" f()");
}
}
class TestThread2 extends TestThread1 {
TestThread2(ThreadGroup g,String name){
super(g,name);
start();
}
public void run(){
ThreadGroup g=getThreadGroup().getParent().getParent();
g.list();
System.out.println("ThreadCount: "+g.activeCount());
Thread[] gAll =new Thread[g.activeCount()];
g.enumerate(gAll);
System.out.println("ThreadCount: "+gAll.length);
for(int i=0; i<gAll.length;i++){
System.out.println(i+" - ");
gAll[i].setPriority(Thread.MIN_PRIORITY);
((TestThread1)gAll[i]).f();
}
g.list();
}
}
=====================
output:
java.lang.ThreadGroup[name=x,maxpri=10]
Thread[one,5,x]
java.lang.ThreadGroup[name=y,maxpri=10]
java.lang.ThreadGroup[name=z,maxpri=10]
Thread[two,5,z]
ThreadCount: 2
ThreadCount: 2
0 -
two f()
1 -
java.lang.NullPointerException
at TestThread2.run(TestAccess.java:44)
(Review ID: 130375)
======================================================================
Name: nt126004 Date: 04/09/2002
FULL PRODUCT VERSION :
java version "1.4.0"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0-b92)
Java HotSpot(TM) Client VM (build 1.4.0-b92, mixed mode)
FULL OPERATING SYSTEM VERSION :
Windows 98 [Version 4.10.2222]
A DESCRIPTION OF THE PROBLEM :
According to Oaks & Wong, "Java Threads, 2nd", p. 33-34,
Thread.enumerate() should return a list containing
Thread.activeCount() objects of type Thread, even if those
objects have no other references, and that such objects
are those which have been constructed and neither exited
from their run() method nor been stopped.
The evidence of the enclosed program shows a different
behavior; activeCount() will report as expected, but
enumerate() fails to return Thread objects with no (other)
references.
The API is silent on all this, as usual.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
1. Run the sample program.
2.
3.
EXPECTED VERSUS ACTUAL BEHAVIOR :
Expected and actual results are noted in the code sample.
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
public class Test extends Thread {
public Test(String s) {
super(s); // save our name
}
public static void main(String[] args) {
{ // (intentional extra block)
int ac = Thread.activeCount();
System.out.println(ac); // prints 2
Thread[] ta = new Thread[10];
for(int i=0;i<10;++i) {
String str = "thread"+i;
ta[i] = new Test(str); // (a thread)
System.out.println("created "+ta[i].getName());
// just to be sure
}
ac = Thread.activeCount();
// i.e., constructed but not exited or stopped
// (according to Oaks & Wong)
System.out.println(ac); // prints 12 (expected)
} // intentional loss of scope
int ac = Thread.activeCount();
System.out.println(ac); // prints 12 (expected - threads were
// constructed and not run-exited or stopped)
Thread tb[] = new Thread[ac];
int n = Thread.enumerate(tb); // should get all those
// constructed threads
System.out.println(n); //prints 1 (unexpected; if activeCount()
// returned 12, enumerate() should give us 12 also)
for(int i=0;i<n;++i) {
System.out.println(tb[i].getName());
// only prints "main"
if(!tb[i].isAlive()) {
// i.e., run() has not been called
System.out.println("starting "+i);
// never executes
tb[i].start(); // exits immediately (see below)
}
}
try {
Thread.sleep(5000);
// maybe we need time for threads to vanish
}
catch (InterruptedException ex) {
}
ac = Thread.activeCount();
System.out.println(ac);
// prints 12 (expected only if they haven't run)
}
public void run() {
System.out.println("thread started");
}
}
---------- END SOURCE ----------
(Review ID: 144715)
======================================================================