java thread问题的不解

starry 2004-12-31 05:44:55
近日在学习java thread,写了一个求素数的程序(其算法当然是不值一看的,只是为了学习)。
但结果颇感奇怪。小弟才疏学浅,不能明白了,还望赐教 :)
程序如下:
public class ThreadTester {
private static class WorkerThread extends Thread {
int count = 0;
public int currentMax = 2;
public boolean isEnd = true;

public WorkerThread() {
}

public void setCount(int i) {
this.count = i;
}

public void run() {
isEnd = false;
boolean prime = true;
for (int j = 2; j < count; j++) {
if (count % j == 0) {
prime = false;
break;
}
}
if (prime) {
currentMax = count;
}
isEnd = true;
}
}

public static void main(String[] args) {
int count = Integer.parseInt(args[0]);
WorkerThread w1 = new WorkerThread();
WorkerThread w2 = new WorkerThread();
WorkerThread w3 = new WorkerThread();
WorkerThread w4 = new WorkerThread();
int i = 3;
w1.start();
w2.start();
w3.start();
w4.start();
while (i < count-4) {
if (w1.isEnd) {
w1.setCount(i++);
w1.run();
}
if (w2.isEnd) {
w2.setCount(i++);
w2.run();
}
if (w3.isEnd) {
w3.setCount(i++);
w3.run();
}
if (w4.isEnd) {
w4.setCount(i++);
w4.run();
}
}
System.out.println(w1.currentMax);
System.out.println(w2.currentMax);
System.out.println(w3.currentMax);
System.out.println(w4.currentMax);
}
}

输入参数100,在我的pc上运算(win2000 prof,P4 1.7G)执行的结果是
83
2
97
2
也就是说有两个thread没有执行!
又换了台dell 6400(redhat linux server2.4,P3 至强 700×4)来执行,结果也差不多,还是感觉有两个thread没有执行。
而后又把参数调到1000000,执行了很久时间(算法很拙嘛~~)。执行过程中,一直top,发现并不是四个cpu都在running,结果也是有两个thread没有执行(输出为2)!
那位大虾解释一下。谢谢
...全文
146 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
JMen 2005-01-01
  • 打赏
  • 举报
回复
二楼说的有道理!
ZheX 2005-01-01
  • 打赏
  • 举报
回复
同意楼上的说法,我觉得最好的测试线程是否运行的方法就是加个计数器。
ForestOcean 2004-12-31
  • 打赏
  • 举报
回复
你的问题很有趣,我将程序改成下列形式:

public class ThreadTester {
private static class WorkerThread extends Thread {
int count = 0;
public int currentMax = 2;
public boolean isEnd = true;

public WorkerThread() {
}

public void setCount(int i) {
this.count = i;
}

public void run() {
isEnd = false;
boolean prime = true;
System.out.println("COUNT="+count);
for (int j = 2; j < count; j++) {
if (count % j == 0) {
prime = false;
break;
}
System.out.print("j=" + j + "\t");
}
if (prime) {
currentMax = count;
}
System.out.println();
isEnd = true;
}
}

public static void main(String[] args) {
int count = Integer.parseInt(args[0]);
WorkerThread w1 = new WorkerThread();
WorkerThread w2 = new WorkerThread();
WorkerThread w3 = new WorkerThread();
WorkerThread w4 = new WorkerThread();
int i = 3;
w1.start();
w2.start();
w3.start();
w4.start();
while (i < count-4) {
System.out.println("No." + i);
if (w1.isEnd) {
System.out.print("w1:" + i + "\t");
w1.setCount(i++);
w1.run();
}
if (w2.isEnd) {
System.out.print("w2:" + i + "\t");
w2.setCount(i++);
w2.run();
}
if (w3.isEnd) {
System.out.print("w3:" + i + "\t");
w3.setCount(i++);
w3.run();
}
if (w4.isEnd) {
System.out.print("w4:" + i + "\t");
w4.setCount(i++);
w4.run();
}
System.out.println();
}
System.out.println("w1" + w1.currentMax);
System.out.println("w2" + w2.currentMax);
System.out.println("w3" + w3.currentMax);
System.out.println("w4" + w4.currentMax);
}
}

然后改命令行为
java ThreadTester 100 >result.txt
看文本文档中的内容,就会发现代码中的问题了。
在每次while的内部,四个进程都会被调用run方法,每次在这个方法返回后才继续执行代码。这也就得到了这个结果。这是因为你的w2和w4接收的数均为偶数,所以它们的currentMax不会发生改变。这并不是CPU的问题。

但有一点要说清楚,就是创建线程和运行线程的方法,并不是调用Thread的run方法,而是Thread.start()。这个调用开动一个新的线程程序并执行它本身的run()方法,如果你统计一下result.txt中COUNT文字的个数,发现它是100个,这里面包括while循环中的3到98的96次调用run方法,和四次在w*.start()时调用的。

关于线程类(Thread类),我们可以通过重载其run()方法,并调用Thread.start()来开启一个新的线程,这个方法是不需要等待run()方法的返回值的。而显式的调用run()方法则和一般的方法调用无差别,直到这个方法中的代码执行结束后这个方法才返回。

呵呵,接分。
beyondtkl 2004-12-31
  • 打赏
  • 举报
回复
你是多CPU的呀?

62,614

社区成员

发帖
与我相关
我的任务
社区描述
Java 2 Standard Edition
社区管理员
  • Java SE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧