一、避免在循環條件中使用複雜表達式
#在不做編譯最佳化的情況下,在循環中,循環條件會被反覆計算,如果不使用複雜表達式,而使循環條件值不變的話,程式將會運行的更快。
範例:
import java.util.vector; class cel { void method (vector vector) { for (int i = 0; i < vector.size (); i++) // violation ; // ... } }
修正:
class cel_fixed { void method (vector vector) { int size = vector.size () for (int i = 0; i < size; i++) ; // ... } }
#2、為'vectors ' 和'hashtables'定義初始大小
jvm為vector擴充大小的時候需要重新建立一個更大的數組,將原原先數組中的內容複製過來,最後,原先的數組再被回收。可見vector容量的擴大是一件頗費時間的事。
通常,預設的10個元素大小是不夠的。你最好能準確的估計你所需要的最佳大小。
範例:
import java.util.vector; 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);
三、在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區塊
四、使用'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 } } }
修正:
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]; system.arraycopy(array1, 0, array2, 0, 100); } }
#五、讓存取實例內變數的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) { _size = size; } private int _size; }
六、避免不需要的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"); } }
修正: 與刪除作業所刪除的中刪除作業。
class dog extends uiso { void method () { 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 { void method () { dog dog = new dog (); unc animal = (unc)dog; // not necessary. object o = (object)dog; // not necessary. } }更正:
class dog extends unc { void method () { dog dog = new dog(); unc animal = dog; object o = dog; } }
八、如果只是找出單一字元的話,用charat()取代startswith()
用一個字元當參數呼叫startswith()也會運作的很好,但從效能角度來看,呼叫用string api無疑是錯誤的!
例:
public class pcts { private void method(string s) { if (s.startswith("a")) { // violation // ... } } }更正
將'startswith()' 替換成'charat()'.
#
public class pcts { private void method(string s) { if ('a' == s.charat(0)) { // ... } } }
、使用移位操作來代替'a / b'操作
"/"是一個很「昂貴」的操作,使用移位操作將會更快更有效。
範例:
public class sp { public static final int num = 16; public void calculate(int a) { int p = a / 4; // should be replaced with "a >> 2". int p2 = a / 8; // should be replaced with "a >> 3". int temp = a / 3; } }修正:
public class sp { public static final int num = 16; public void calculate(int a) { int p = a >> 2; int p2 = a >> 3; int temp = a / 3; // 不能转换成位移操作 } }
十、使用移位運算取代'a * b'
同上。
[i]但我個人認為,除非是在一個非常大的循環內,性能非常重要,而且你很清楚你自己在做什麼,方可使用這種方法。否則提高效能所帶來的程式晚讀性的降低將是不合算的。
範例:
public class smul { public void calculate(int a) { int mul = a * 4; // should be replaced with "a << 2". int mul2 = 8 * a; // should be replaced with "a << 3". int temp = a * 3; } }修正:
package opt; public class smul { public void calculate(int a) { int mul = a << 2; int mul2 = a << 3; int temp = a * 3; // 不能转换 } }
十一、在字串相加的時候,使用 ' '代替" ",如果該字串只有一個字元的話
範例:
public class str { public void method(string s) { string string = s + "d" // violation. string = "abc" + "d" // violation. } }
修正:
將一個字元的字串替換成' '
public class str { public void method(string s) { string string = s + 'd' string = "abc" + 'd' } }
十二、不要在循环中调用synchronized(同步)方法
方法的同步需要消耗相当大的资料,在一个循环中调用它绝对不是一个好主意。
例子:
import java.util.vector; public class syn { public synchronized void method (object o) { } private void test () { for (int i = 0; i < vector.size(); i++) { method (vector.elementat(i)); // violation } } private vector vector = new vector (5, 5); }
更正:
不要在循环体中调用同步方法,如果必须同步的话,推荐以下方式:
import java.util.vector; public class syn { public void method (object o) { } private void test () { synchronized{//在一个同步块中执行非同步方法 for (int i = 0; i < vector.size(); i++) { method (vector.elementat(i)); } } } private vector vector = new vector (5, 5); }
十三、将try/catch块移出循环
把try/catch块放入循环体内,会极大的影响性能,如果编译jit被关闭或者你所使用的是一个不带jit的jvm,性能会将下降21%之多!
例子:
import java.io.fileinputstream; public class try { void method (fileinputstream fis) { for (int i = 0; i < size; i++) { try { // violation _sum += fis.read(); } catch (exception e) {} } } private int _sum; }
更正:
将try/catch块移出循环
void method (fileinputstream fis) { try { for (int i = 0; i < size; i++) { _sum += fis.read(); } } catch (exception e) {} }
十四、对于boolean值,避免不必要的等式判断
将一个boolean值与一个true比较是一个恒等操作(直接返回该boolean变量的值). 移走对于boolean的不必要操作至少会带来2个好处:
1)代码执行的更快 (生成的字节码少了5个字节);
2)代码也会更加干净 。
例子:
public class ueq { boolean method (string string) { return string.endswith ("a") == true; // violation } }
更正:
class ueq_fixed { boolean method (string string) { return string.endswith ("a"); } }
十五、对于常量字符串,用'string' 代替 'stringbuffer'
常量字符串并不需要动态改变长度。
例子:
public class usc { string method () { stringbuffer s = new stringbuffer ("hello"); string t = s + "world!"; return t; } }
更正:
把stringbuffer换成string,如果确定这个string不会再变的话,这将会减少运行开销提高性能。
十六、用'stringtokenizer' 代替 'indexof()' 和'substring()'
字符串的分析在很多应用中都是常见的。使用indexof()和substring()来分析字符串容易导致 stringindexoutofboundsexception。而使用stringtokenizer类来分析字符串则会容易一些,效率也会高一些。
例子:
public class ust { void parsestring(string string) { int index = 0; while ((index = string.indexof(".", index)) != -1) { system.out.println (string.substring(index, string.length())); } } }
十七、使用条件操作符替代"if (cond) return; else return;" 结构
条件操作符更加的简捷
例子:
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); } }
十八、使用条件操作符代替"if (cond) a = b; else a = c;" 结构
例子:
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<v.size();i++) { o = v.elementat(i); } } }
二十、确定 stringbuffer的容量
stringbuffer的构造器会创建一个默认大小(通常是16)的字符数组。在使用中,如果超出这个大小,就会重新分配内存,创建一个更大的数组,并将原先的数组复制过来,再丢弃旧的数组。在大多数情况下,你可以在创建stringbuffer的时候指定大小,这样就避免了在容量不够的时候自动增长,以提高性能。
例子:
public class rsbc { void method () { stringbuffer buffer = new stringbuffer(); // violation buffer.append ("hello"); } }
更正:
为stringbuffer提供寝大小。
public class rsbc { void method () { stringbuffer buffer = new stringbuffer(max); buffer.append ("hello"); } private final int max = 100; }
二十一、尽可能的使用栈变量
如果一个变量需要经常访问,那么你就需要考虑这个变量的作用域了。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; }
二十二、不要总是使用取反操作符(!)
取反操作符(!)降低程序的可读性,所以不要总是使用。
例子:
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中關於程式效能最佳化的實例講解的詳細內容。更多資訊請關注PHP中文網其他相關文章!

新興技術對Java的平台獨立性既有威脅也有增強。 1)雲計算和容器化技術如Docker增強了Java的平台獨立性,但需要優化以適應不同雲環境。 2)WebAssembly通過GraalVM編譯Java代碼,擴展了其平台獨立性,但需與其他語言競爭性能。

不同JVM實現都能提供平台獨立性,但表現略有不同。 1.OracleHotSpot和OpenJDKJVM在平台獨立性上表現相似,但OpenJDK可能需額外配置。 2.IBMJ9JVM在特定操作系統上表現優化。 3.GraalVM支持多語言,需額外配置。 4.AzulZingJVM需特定平台調整。

平台獨立性通過在多種操作系統上運行同一套代碼,降低開發成本和縮短開發時間。具體表現為:1.減少開發時間,只需維護一套代碼;2.降低維護成本,統一測試流程;3.快速迭代和團隊協作,簡化部署過程。

Java'splatformindependencefacilitatescodereusebyallowingbytecodetorunonanyplatformwithaJVM.1)Developerscanwritecodeonceforconsistentbehavioracrossplatforms.2)Maintenanceisreducedascodedoesn'tneedrewriting.3)Librariesandframeworkscanbesharedacrossproj

要解決Java應用程序中的平台特定問題,可以採取以下步驟:1.使用Java的System類查看系統屬性以了解運行環境。 2.利用File類或java.nio.file包處理文件路徑。 3.根據操作系統條件加載本地庫。 4.使用VisualVM或JProfiler優化跨平台性能。 5.通過Docker容器化確保測試環境與生產環境一致。 6.利用GitHubActions在多個平台上進行自動化測試。這些方法有助於有效地解決Java應用程序中的平台特定問題。

類加載器通過統一的類文件格式、動態加載、雙親委派模型和平台無關的字節碼,確保Java程序在不同平台上的一致性和兼容性,實現平台獨立性。

Java編譯器生成的代碼是平台無關的,但最終執行的代碼是平台特定的。 1.Java源代碼編譯成平台無關的字節碼。 2.JVM將字節碼轉換為特定平台的機器碼,確保跨平台運行但性能可能不同。

多線程在現代編程中重要,因為它能提高程序的響應性和資源利用率,並處理複雜的並發任務。 JVM通過線程映射、調度機制和同步鎖機制,在不同操作系統上確保多線程的一致性和高效性。


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

Video Face Swap
使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

熱工具

VSCode Windows 64位元 下載
微軟推出的免費、功能強大的一款IDE編輯器

Atom編輯器mac版下載
最受歡迎的的開源編輯器

EditPlus 中文破解版
體積小,語法高亮,不支援程式碼提示功能

Dreamweaver CS6
視覺化網頁開發工具

SublimeText3 英文版
推薦:為Win版本,支援程式碼提示!