我有一个程序可以通过将大文件拆分成块,排序块并将它们合并到最终排序文件中来对大文件进行排序。应用程序运行一个线程,用于从/向文件加载/保存数据 - 只有一个线程执行I / O操作。还有两个线程接收块数据,对其进行排序,然后将排序后的数据发送回执行I / O的线程。
所以通常有4个线程在运行 - 主线程,加载/保存数据的线程和两个对数据进行排序的线程。
我认为在执行过程中我将看到1个没有占用任何CPU时间的休眠线程(主)和3个每个使用1个CPU核心的活动线程。
当我在具有超线程(24个CPU)的双6核处理器机器上运行此程序时,我看到所有24个CPU都加载了100%!
最初我认为排序算法是mutithreaded,但在查看java源代码后我发现它不是。
我正在使用简单的Collections.sort(LinkedList)对数据进行排序......
这里有一些细节:
# java -version java version "1.6.0_26" Java(TM) SE Runtime Environment (build 1.6.0_26-b03) Java HotSpot(TM) 64-Bit Server VM (build 20.1-b02, mixed mode) # uname -a Linux 2.6.32-28-server #55-Ubuntu SMP Mon Jan 10 23:57:16 UTC 2011 x86_64 GNU/Linux
我正在使用nmon来监控处理器加载。
我将不胜感激对此案例的任何解释以及有关如何控制CPU负载的任何建议,因为此特定任务不会为其他应用程序留出CPU时间
[UPDATE] 我使用jvisualvm来计算线程 - 它只显示我所知道的线程。此外,我做了一个简单的测试程序(见下文),只运行一个主线程并得到完全相同的结果 - 所有24个处理器在代码执行期间几乎忙于100%
public class Test {
public void run(){
Random r = new Random();
int len = r.nextInt(10) + 5000000;
LinkedList<String> list = new LinkedList<String>();
for (int i=0; i<len; i++){
list.add(new String("test" + r.nextInt(50000000)));
}
System.out.println("Inserted " + list.size() + " items");
list.clear();
}
public static void main(String[] argv){
Test t = new Test();
t.run();
System.out.println("Done");
}
}
[UPDATE]
这是我在运行上面的程序时使用的截图(使用了nmon):
http://imageshack.us/photo/my-images/716/cpuload.png/
答案 0 :(得分:1)
我建议,这是一个非常的问题,而不是一个java问题,为了解决它,我会看一下top
命令,该命令提供有关每个进程的cpu使用情况的信息。我预测以下结果:你将看到一个使用接近100%cpu-time的java线程(这是好的,因为top中的每个进程百分比是相对于一个(虚拟)核心),也许是第二个和第三个java线程减少cpu使用(I / O线程)。根据gc的选择,您甚至可能会发现一个或多个gc-Threads,但不到20个。
HotSpot不会(甚至不能据我所知)自己并行化顺序任务。