天天看點

Java程式性能優化(1)

後面幾條似乎有點不那麼必要?

from:http://java.chinaitlab.com/advance/839649.html

一、避免在循環條件中使用複雜表達式

  在不做編譯優化的情況下,在循環中,循環條件會被反複計算,如果不使用複雜表達式,而使循環條件值不變的話,程式将會運作的更快。

  例子:

  import java.util.Vector;

  class CEL {

  void method (Vector vector) {

  for (int i = 0; i < vector.size (); i++)  // Violation

  ; // ...

  }

  更正:

  class CEL_fixed {

  int size = vector.size ()

  for (int i = 0; i < size; i++)

  二、為'Vectors' 和 'Hashtables'定義初始大小

  JVM為Vector擴充大小的時候需要重新建立一個更大的數組,将原原先數組中的内容複制過來,最後,原先的數組再被回收。可見Vector

容量的擴大是一個頗費時間的事。

  通常,預設的10個元素大小是不夠的。你最好能準确的估計你所需要的最佳大小。

  public class DIC {

  public void addObjects (Object[] o) {

  // if length > 10, Vector needs to expand

  for (int i = 0; i< o.length;i++) {

  v.add(o);   // capacity before it can add more elements.

  public Vector v = new Vector();  // no initialCapacity.

  自己設定初始大小。

  public Vector v = new Vector(20);

  public Hashtable hash = new Hashtable(10);

  參考資料:

  Dov Bulka, "Java Performance and

Scalability Volume 1: Server-Side Programming

  Techniques" Addison Wesley, ISBN: 0-201-70429-3 pp.55 – 57

  三、在finally塊中關閉Stream

  程式中使用到的資源應當被釋放,以避免資源洩漏。這最好在finally塊中去做。不管程式執行的結果如何,finally塊總是會執行的,以

確定資源的正确關閉。

  import java.io.*;

  public class CS {

  public static void main (String args[]) {

  CS cs = new CS ();

  cs.method ();

  public void method () {

  try {

  FileInputStream fis = new FileInputStream ("CS.java");

  int count = 0;

  while (fis.read () != -1)

  count++;

  System.out.println (count);

  fis.close ();

  } catch (FileNotFoundException e1) {

  } catch (IOException e2) {

  在最後一個catch後添加一個finally塊

  Peter Haggar: "Practical Java -

Programming Language Guide".

  Addison Wesley, 2000, pp.77-79

  四、使用'System.arraycopy ()'代替通過來循環複制數組

  'System.arraycopy ()' 要比通過循環來複制數組快的多。

  public class IRB

  {

  void method () {

  int[] array1 = new int [100];

  for (int i = 0; i < array1.length; i++) {

  array1 [i] = i;

  int[] array2 = new int [100];

  for (int i = 0; i < array2.length; i++) {

  array2 [i] = array1 [i];                 // Violation

更正:

  System.arraycopy(array1, 0, array2, 0, 100);

  http://www.cs.cmu.edu/~jch/java/speed.html

  五、讓通路執行個體内變量的getter/setter方法變成”final”

  簡單的getter/setter方法應該被置成final,這會告訴編譯器,這個方法不會被重載,是以,可以變成”inlined”

  class MAF {

  public void setSize (int size) {

  _size = size;

  private int _size;

  class DAF_fixed {

  final public void setSize (int size) {

  Warren N. and Bishop P. (1999), "Java in Practice", p. 4-5

  Addison-Wesley, ISBN 0-201-36065-9

  六、避免不需要的instanceof操作

  如果左邊的對象的靜态類型等于右邊的,instanceof表達式傳回永遠為true。

  public class UISO {

  public UISO () {}

  class Dog extends UISO {

  void method (Dog dog, UISO u) {

  Dog d = dog;

  if (d instanceof UISO) // always true.

  System.out.println("Dog is a UISO");

  UISO uiso = u;

  if (uiso instanceof Object) // always true.

  System.out.println("uiso is an Object");

  删掉不需要的instanceof操作。

  Dog d;

  System.out.println ("Dog is an UISO");

  System.out.println ("UISO is an UISO");

  七、避免不需要的造型操作

  所有的類都是直接或者間接繼承自Object。同樣,所有的子類也都隐含的“等于”其父類。那麼,由子類造型至父類的操作就是不必要的了。

  class UNC {

  String _id = "UNC";

  class Dog extends UNC {

  Dog dog = new Dog ();

  UNC animal = (UNC)dog;  // not necessary.

  Object o = (Object)dog;         // not necessary.

  Dog dog = new Dog();

  UNC animal = dog;

  Object o = dog;

  Nigel Warren, Philip Bishop: "Java in Practice - Design Styles and

Idioms

  for Effective Java".  Addison-Wesley, 1999. pp.22-23