十七、使用条件操作符替代\结构
条件操作符更加的简捷 例子:
public class IF {
public int method(boolean isDone) { if (isDone) { return 0; } else {
return 10; } } }
更正:
public class IF {
public int method(boolean isDone) { return (isDone ? 0 : 10); } }
十八、使用条件操作符代替\结构
例子:
public class IFAS {
void method(boolean isTrue) { if (isTrue) { _value = 0; } else {
_value = 1; } }
private int _value = 0; }
更正:
public class IFAS {
void method(boolean isTrue) {
_value = (isTrue ? 0 : 1); // compact expression. }
private int _value = 0; }
十九、不要在循环体中实例化变量
在循环体中实例化临时变量将会增加内存消耗
例子:
import java.util.Vector; public class LOOP {
void method (Vector v) {
for (int i=0;i < v.size();i++) { Object o = new Object(); o = v.elementAt(i);
} } }
更正:
在循环体外定义变量,并反复使用 import java.util.Vector; public class LOOP {
void method (Vector v) { Object o;
for (int i=0;i 二十、确定 StringBuffer的容量 StringBuffer 的构造器会创建一个默认大小(通常是16)的字符数组。在使用中,如果超出这个大小,就会重新分配内存,创建一个更大的数组,并将原先的数组复制过来,再丢弃旧的数组。在大多数情况下,你可以在创建 StringBuffer的时候指定大小,这样就避免了在容量不够的时候自动增长,以提高性能。 例子: public class RSBC { void method () { StringBuffer buffer = new StringBuffer(); // violation buffer.append (\ } } 更正: 为StringBuffer提供寝大小。 public class RSBC { void method () { StringBuffer buffer = new StringBuffer(MAX); buffer.append (\ } private final int MAX = 100; } 参考资料: Dov Bulka, \Techniques\– 31 二十一、尽可能的使用栈变量 如果一个变量需要经常访问,那么你就需要考虑这个变量的作用域了。static? local?还是实例变量?访问静态变量和实例变量将会比访问局部变量多耗费2-3个时钟周期。 例子: public class USV { void getSum (int[] values) { for (int i=0; i < value.length; i++) { _sum += value[i]; // violation. } } void getSum2 (int[] values) { for (int i=0; i < value.length; i++) { _staticSum += value[i]; } } private int _sum; private static int _staticSum; } 更正: 如果可能,请使用局部变量作为你经常访问的变量。 你可以按下面的方法来修改getSum()方法: void getSum (int[] values) { int sum = _sum; // temporary local variable. for (int i=0; i < value.length; i++) { sum += value[i]; } _sum = sum; } 参考资料: Peter Haggar: \Addison Wesley, 2000, pp.122 – 125 二十二、不要总是使用取反操作符(!) 取反操作符(!)降低程序的可读性,所以不要总是使用。 例子: public class DUN { boolean method (boolean a, boolean b) { if (!a) return !a; else return !b; } } 更正: 如果可能不要使用取反操作符(!) 二十三、与一个接口进行instanceof操作 基于接口的设计通常是件好事,因为它允许有不同的实现,而又保持灵活。只要可能,对一个对象进行instanceof操作,以判断它是否某一接口要比是否某一个类要快。 例子: public class INSOF { private void method (Object o) { if (o instanceof InterfaceBase) { } // better if (o instanceof ClassBase) { } // worse. } } class ClassBase {} interface InterfaceBase { Java在九十年代中期出现以后,在赢得赞叹的同时,也引来了一些批评。赢得的赞叹主要是Java的跨平台的操作性,即所谓的”Write Once,Run Anywhere”.但由于Java的性能和运行效率同C相比,仍然有很大的差距,从而引来了很多的批评。 对于服务器端的应用程序,由于不大涉及到界面设计和程序的频繁重启,Java的性能问题看似不大明显,从而一些Java的技术,如JSP,Se rvlet,EJB等在服务器端编程方面得到了很大的应用,但实际上,Java的性能问题在服务器端依然存在。下面我将分四个方面来讨论Java的性能和执行效率以及提高J ava性能的一些方法。 一.关于性能的基本知识 1.性能的定义 在我们讨论怎样提高Java的性能之前,我们需要明白“性能“的真正含义。我们一般定义如下五个方面作为评判性能的标准。 1)运算的性能----哪一个算法的执行性能最好 2)内存的分配----程序需要分配多少内存,运行时的效率和性能最高。 3)启动的时间----程序启动需要多少时间。 4)程序的可伸缩性-----程序在用户负载过重的情况下的表现。 5)性能的认识------用户怎样才能认识到程序的性能。 对于不同的应用程序,对性能的要求也不同。例如,大部分的应用程序在启动时需要较长的时间,从而对启动时间的要求有所降低;服务器端的应用程序通常都分配有较大的内存空间,所以对内存的要求也有所降低。但是,这并不是所这两方面的性能可以被忽略。其次,算法的性能对于那些把商务逻辑运用到事务性操作的应用程序来讲非常重要。总的来讲,对应用程序的要求将决定对各个性能的优先级。 2.怎样才能提高JAVA的性能 提高JAVA的性能,一般考虑如下的四个主要方面: (1)程序设计的方法和模式 一个良好的设计能提高程序的性能,这一点不仅适用于JAVA,也适用也任何的编程语言。因为它充分利用了各种资源,如内存,CPU,高速缓存,对象缓冲池及多线程,从而设计出高性能和可伸缩性强的系统。 当然,为了提高程序的性能而改变原来的设计是比较困难的,但是,程序性能的重要性常常要高于设计上带来的变化。因此,在编程开始之前就应该有一个好的设计模型和方法。 (2) JAVA布署的环境。 JAVA布署的环境就是指用来解释和执行JAVA字节码的技术,一般有如下五种。即解释指令技术(Interpreter Technology),及时编译的技术(Just In Time Compilier Technology), 适应性优化技术(Adaptive Optimization Technology), 动态优化,提前编译为机器码的技术(Dynamic Optimization,Ahead Of Time Technology)和编译为机器码的技术(Translator Technology). 这些技术一般都通过优化线程模型,调整堆和栈的大小来优化JAVA的性能。在考虑提高JAVA的性能时,首先要找到影响JAVA性能的瓶颈(B ottleNecks),在确认了设计的合理性后,应该调整JAVA布署的环境,通过改变一些参数来提高JAVA应用程序的性能。具体内容见第二节。