![java筆試--運算符_第1頁](http://file2.renrendoc.com/fileroot_temp3/2021-6/15/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f5/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f51.gif)
![java筆試--運算符_第2頁](http://file2.renrendoc.com/fileroot_temp3/2021-6/15/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f5/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f52.gif)
![java筆試--運算符_第3頁](http://file2.renrendoc.com/fileroot_temp3/2021-6/15/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f5/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f53.gif)
![java筆試--運算符_第4頁](http://file2.renrendoc.com/fileroot_temp3/2021-6/15/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f5/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f54.gif)
![java筆試--運算符_第5頁](http://file2.renrendoc.com/fileroot_temp3/2021-6/15/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f5/fa3f510e-dc9d-4cbc-a4be-2624de4fc1f55.gif)
版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領
文檔簡介
1、自增(+)和自減(-)運算符 我們先來回答幾個問題吧: Java代碼 1. inti=0; 2. intj=i+; 3. intk=-i; int i = 0;int j = i+;int k = -i;這段代碼運行后,i等于多少?j等于多少?k等于多少?太簡單了?好,繼續(xù): Java代碼 1. inti=0; 2. intj=i+i; 3. intk=-i+i-; int i = 0;int j = i+ + +i;int k = -i + i-;代碼執(zhí)行后i、j、k分別等于多少呢?還是很簡單?好,再繼續(xù): Java代碼 1. inti=0; 2. System.out.println(i+
2、); int i=0;System.out.println(i+);這段代碼運行后輸出結(jié)果是什么?0?1? Java代碼 1. floatf=0.1F; 2. f+; 3. doubled=0.1D; 4. d+; 5. charc=a; 6. c+; float f=0.1F;f+;double d=0.1D;d+;char c=a;c+;上面這段代碼可以編譯通過嗎?為什么?如果你能順利回答到這里,說明你對自增和自減運算符的掌握已經(jīng)很好了。 為了分析出上面提出的幾個問題,我們首先來回顧一下相關知識: 自增(+):將變量的值加1,分前綴式(如+i)和后綴式(如i+)。前綴式是先加1再使用;后綴
3、式是先使用再加1。 自減(-):將變量的值減1,分前綴式(如-i)和后綴式(如i-)。前綴式是先減1再使用;后綴式是先使用再減1。 在第一個例子中,int j=i+;是后綴式,因此i的值先被賦予j,然后再自增1,所以這行代碼運行后,i=1、j=0;而int k=-i;是前綴式,因此i先自減1,然后再將它的值賦予k,因此這行代碼運行后,i=0、k=0。 在第二個例子中,對于int j=i+ + +i;,首先運行i+,i的值0被用于加運算(+),之后i自增值變?yōu)?,然后運行+i,i先自增變?yōu)?,之后被用于加運算,最后將i兩次的值相加的結(jié)果0+2=2賦給j,因此這行代碼運行完畢后i=2、j=2;對于
4、int k=-i + i-;用一樣的思路分析,具體過程在此不再贅述,結(jié)果應該是i=0、k=2。 自增與自減運算符還遵循以下規(guī)律: 1. 可以用于整數(shù)類型byte、short、int、long,浮點類型float、double,以及字符串類型char。 2. 在Java5.0及以上版本中,它們可以用于基本類型對應的包裝器類Byte、Short、Integer、Long、Float、Double、Character。 3. 它們的運算結(jié)果的類型與被運算的變量的類型相同。 下面的這個例子驗證以上列出的規(guī)律,它可以編譯通過并執(zhí)行。 Java代碼 1. publicclassTest 2. public
5、staticvoidmain(Stringargs) 3. /整型 4. byteb=0; 5. b+; 6. /整型 7. longl=0; 8. l+; 9. /浮點型 10. doubled=0.0; 11. d+; 12. /字符串 13. charc=a; 14. c+; 15. /基本類型包裝器類 16. Integeri=newInteger(0); 17. i+; 18. 19. public class Test public static void main(String args) / 整型byte b = 0;b+;/ 整型long l = 0;l+;/ 浮點型doub
6、le d = 0.0;d+;/ 字符串char c = a;c+;/ 基本類型包裝器類Integer i = new Integer(0);i+;按位運算符 你還能說出來按位運算符一共有哪幾種嗎?對比下面的列表看看,有沒有從你的記憶中消失了的: 1. 按位與運算(&):二元運算符。當被運算的兩個值都為1時,運算結(jié)果為1;否則為0。 2. 按位或運算(|):二元運算符。當被運算的兩個值都為0時,運算結(jié)果為0;否則為1。 3. 按位異或運算():二元運算符。當被運算的兩個值中任意一個為1,另一個為0時,運算結(jié)果為1;否則為0。 4. 按位非運算():一元運算符。當被運算的值為1時,運算結(jié)果為0;當
7、被運算的值為0時,運算結(jié)果為1。 這里不像我們看到的邏輯運算符(與運算&、或運算|、非運算!)操作的是布爾值true或false,或者是一個能產(chǎn)生布爾值的表達式;“按位運算符”所指的“位”就是二進制位,因此它操作的是二進制的0和1。在解釋按位運算符的執(zhí)行原理時,我們順便說說它們和邏輯運算符的區(qū)別。 list=1 邏輯運算符只能操作布爾值或者一個能產(chǎn)生布爾值的表達式;按位運算符能操作整型值,包括byte、short、int、long,但是不能操作浮點型值(即float和double),它還可以操作字符型(char)值。按位運算符不能夠操作對象,但是在Java5.0及以上版本中,byte、shor
8、t、int、long、char所對應的包裝器類是個例外,因為JAVA虛擬機會自動將它們轉(zhuǎn)換為對應的基本類型的數(shù)據(jù)。 下面的例子驗證了這條規(guī)律: Java代碼 1. publicclassBitOperatorTest 2. publicstaticvoidmain(Stringargs) 3. /整型 4. byteb1=10,b2=20; 5. System.out.println(byte)10&(byte)20=+(b1&b2); 6. /字符串型 7. charc1=a,c2=A; 8. System.out.println(char)a|(char)A=+(c1|c2); 9. /基
9、本類型的包裝器類 10. Longl1=newLong(555),l2=newLong(666); 11. System.out.println(Long)555(Long)666=+(l1l2); 12. /浮點型 13. floatf1=0.8F,f2=0.5F; 14. /編譯報錯,按位運算符不能用于浮點數(shù)類型 15. /System.out.println(float)0.8&(float)0.5=+(f1&f2); 16. 17. public class BitOperatorTest public static void main(String args) / 整型byte b1
10、 = 10, b2 = 20;System.out.println(byte)10 & (byte)20 = + (b1 & b2);/ 字符串型char c1 = a, c2 = A;System.out.println(char)a | (char)A = + (c1 | c2);/ 基本類型的包裝器類Long l1 = new Long(555), l2 = new Long(666);System.out.println(Long)555 (Long)666 = + (l1 l2);/ 浮點型float f1 = 0.8F, f2 = 0.5F;/ 編譯報錯,按位運算符不能用于浮點數(shù)類
11、型/ System.out.println(float)0.8 & (float)0.5 = + (f1 & f2);運行結(jié)果: (byte)10 & (byte)20 = 0 (char)a | (char)A = 97 (Long)555 (Long)666 = 177 邏輯運算符的運算遵循短路形式,而按位運算符則不是。所謂短路就是一旦能夠確定運算的結(jié)果,就不再進行余下的運算。下面的例子更加直觀地展現(xiàn)了短路與非短路的區(qū)別: Java代碼 1. publicclassOperatorTest 2. publicbooleanleftCondition() 3. System.out.prin
12、tln(執(zhí)行-返回值:false;方法:leftCondition(); 4. returnfalse; 5. 6. 7. publicbooleanrightCondition() 8. System.out.println(執(zhí)行-返回值:true;方法:rightCondition(); 9. returntrue; 10. 11. 12. publicintleftNumber() 13. System.out.println(執(zhí)行-返回值:0;方法:leftNumber(); 14. return0; 15. 16. 17. publicintrightNumber() 18. Sys
13、tem.out.println(執(zhí)行-返回值:1;方法:rightNumber(); 19. return1; 20. 21. 22. publicstaticvoidmain(Stringargs) 23. OperatorTestot=newOperatorTest(); 24. 25. if(ot.leftCondition()&ot.rightCondition() 26. /dosomething 27. 28. System.out.println(); 29. 30. inti=ot.leftNumber()&ot.rightNumber(); 31. 32. public cl
14、ass OperatorTest public boolean leftCondition() System.out.println(執(zhí)行-返回值:false;方法:leftCondition();return false;public boolean rightCondition() System.out.println(執(zhí)行-返回值:true;方法:rightCondition();return true;public int leftNumber() System.out.println(執(zhí)行-返回值:0;方法:leftNumber();return 0;public int right
15、Number() System.out.println(執(zhí)行-返回值:1;方法:rightNumber();return 1;public static void main(String args) OperatorTest ot = new OperatorTest();if (ot.leftCondition() & ot.rightCondition() / do somethingSystem.out.println();int i = ot.leftNumber() & ot.rightNumber();運行結(jié)果: 執(zhí)行-返回值:false;方法:leftCondition() 執(zhí)行
16、-返回值:0;方法:leftNumber() 執(zhí)行-返回值:1;方法:rightNumber() 運行結(jié)果已經(jīng)很明顯地顯示了短路和非短路的區(qū)別,我們一起來分析一下產(chǎn)生這個運行結(jié)果的原因。當運行“ot.leftCondition() & ot.rightCondition()”時,由于方法leftCondition()返回了false,而對于“&”運算來說,必須要運算符兩邊的值都為true時,運算結(jié)果才為true,因此這時候就可以確定,不論rightCondition()的返回值是什么,“ot.leftCondition() & ot.rightCondition()”的運算值已經(jīng)可以確定是fa
17、lse,由于邏輯運算符是短路的形式,因此在這種情況下,rightCondition()方法就不再被運行了。 而對于“ot.leftNumber() & ot.rightNumber()”,由于“l(fā)eftNumber()”的返回值是0,對于按位運算符“&”來說,必須要運算符兩邊的值都是1時,運算結(jié)果才是1,因此這時不管“rightNumber()”方法的返回值是多少,“ot.leftNumber() & ot.rightNumber()”的運算結(jié)果已經(jīng)可以確定是0,但是由于按位運算符是非短路的,所以rightNumber()方法還是被執(zhí)行了。這就是短路與非短路的區(qū)別。 /list 移位運算符 移
18、位運算符和按位運算符一樣,同屬于位運算符,因此移位運算符的位指的也是二進制位。它包括以下幾種: 1. 左移位():將操作符左側(cè)的操作數(shù)向右移動操作符右側(cè)指定的位數(shù)。移動的規(guī)則是,如果被操作數(shù)的符號為正,則在二進制的高位補0;如果被操作數(shù)的符號為負,則在二進制的高位補1。 3. 無符號右移位():將操作符左側(cè)的操作數(shù)向右移動操作符右側(cè)指定的位數(shù)。移動的規(guī)則是,無論被操作數(shù)的符號是正是負,都在二進制位的高位補0。 注意,移位運算符不存在“無符號左移位()”一說。與按位運算符一樣,移位運算符可以用于byte、short、int、long等整數(shù)類型,和字符串類型char,但是不能用于浮點數(shù)類型floa
19、t、double;當然,在Java5.0及以上版本中,移位運算符還可用于byte、short、int、long、char對應的包裝器類。我們可以參照按位運算符的示例寫一個測試程序來驗證,這里就不再舉例了。 與按位運算符不同的是,移位運算符不存在短路不短路的問題。 寫到這里就不得不提及一個在面試題中經(jīng)常被考到的題目: 引用請用最有效率的方法計算出2乘以8等于幾? 這里所謂的最有效率,實際上就是通過最少、最簡單的運算得出想要的結(jié)果,而移位是計算機中相當基礎的運算了,用它來實現(xiàn)準沒錯了。左移位“”把被操作數(shù)每向左移動一位,效果等同于將被操作數(shù)乘以2,而2*8=(2*2*2*2),就是把2向左移位3次
20、。因此最有效率的計算2乘以8的方法就是“23”。 最后,我們再來考慮一種情況,當要移位的位數(shù)大于被操作數(shù)對應數(shù)據(jù)類型所能表示的最大位數(shù)時,結(jié)果會是怎樣呢?比如,135=?呢? 這里就涉及到移位運算的另外一些規(guī)則: 1. byte、short、char在做移位運算之前,會被自動轉(zhuǎn)換為int類型,然后再進行運算。 2. byte、short、int、char類型的數(shù)據(jù)經(jīng)過移位運算后結(jié)果都為int型。 3. long經(jīng)過移位運算后結(jié)果為long型。 4. 在左移位()運算時,如果要移位的位數(shù)大于被操作數(shù)對應數(shù)據(jù)類型所能表示的最大位數(shù),那么先將要求移位數(shù)對該類型所能表示的最大位數(shù)求余后,再將被操作數(shù)移
21、位所得余數(shù)對應的數(shù)值,效果不變。比如135=1(35%32)=1)運算和無符號右移位()運算,當要移位的位數(shù)大于被操作數(shù)對應數(shù)據(jù)類型所能表示的最大位數(shù)時,那么先將要求移位數(shù)對該類型所能表示的最大位數(shù)求余后,再將被操作數(shù)移位所得余數(shù)對應的數(shù)值,效果不變。比如10035=100(35%32)=1003=12。 下面的測試代碼驗證了以上的規(guī)律: Java代碼 1. publicabstractclassTest 2. publicstaticvoidmain(Stringargs) 3. System.out.println(13=+(13); 4. System.out.println(byte)
22、135=+(byte)1(32+3); 5. System.out.println(short)135=+(short)1(32+3); 6. System.out.println(char)135=+(char)1(32+3); 7. System.out.println(135=+(1(32+3); 8. System.out.println(1L67=+(1L(64+3); 9. /此處需要Java5.0及以上版本支持 10. System.out.println(newInteger(1)3=+(newInteger(1)3=+(100003); 12. System.out.prin
23、tln(1000035=+(10000(32+3); 13. System.out.println(10000L67=+(10000L(64+3); 14. 15. public abstract class Test public static void main(String args) System.out.println(1 3 = + (1 3);System.out.println(byte) 1 35 = + (byte) 1 (32 + 3);System.out.println(short) 1 35 = + (short) 1 (32 + 3);System.out.pri
24、ntln(char) 1 35 = + (char) 1 (32 + 3);System.out.println(1 35 = + (1 (32 + 3);System.out.println(1L 67 = + (1L (64 + 3);/ 此處需要Java5.0及以上版本支持System.out.println(new Integer(1) 3 = + (new Integer(1) 3 = + (10000 3);System.out.println(10000 35 = + (10000 (32 + 3);System.out.println(10000L 67 = + (10000L
25、 (64 + 3);運行結(jié)果: 1. 1 3 = 8 2. (byte) 1 35 = 8 3. (short) 1 35 = 8 4. (char) 1 35 = 8 5. 1 35 = 8 6. 1L 67 = 8 7. new Integer(1) 3 = 1250 9. 10000 35 = 1250 10. 10000L 67 = 1250 下一期預告:JAVA面試題解惑系列(十二)你真的了解數(shù)組嗎? 11:00 瀏覽 (111) 評論 (0) 分類: java筆試面試 2009-07-01縮略顯示JAVA筆試面試必考題系列(十)話說多線程JAVA面試題解惑系列(十)話說多線程關鍵字
26、: java 面試題 多線程 thread 線程池 synchronized 死鎖作者:臧圩人(zangweiren) 網(wǎng)址: 轉(zhuǎn)載請注明出處! 線程或者說多線程,是我們處理多任務的強大工具。線程和進程是不同的,每個進程都是一個獨立運行的程序,擁有自己的變量,且不同進程間的變量不能共享;而線程是運行在進程內(nèi)部的,每個正在運行的進程至少有一個線程,而且不同的線程之間可以在進程范圍內(nèi)共享數(shù)據(jù)。也就是說進程有自己獨立的存儲空間,而線程是和它所屬的進程內(nèi)的其他線程共享一個存儲空間。線程的使用可以使我們能夠并行地處理一些事情。線程通過并行的處理給用戶帶來更好的使用體驗,比如你使用的郵件系統(tǒng)(outloo
27、k、Thunderbird、foxmail等),你當然不希望它們在收取新郵件的時候,導致你連已經(jīng)收下來的郵件都無法閱讀,而只能等待收取郵件操作執(zhí)行完畢。這正是線程的意義所在。 實現(xiàn)線程的方式 實現(xiàn)線程的方式有兩種: 1. 繼承java.lang.Thread,并重寫它的run()方法,將線程的執(zhí)行主體放入其中。 2. 實現(xiàn)java.lang.Runnable接口,實現(xiàn)它的run()方法,并將線程的執(zhí)行主體放入其中。 這是繼承Thread類實現(xiàn)線程的示例: Java代碼 1. publicclassThreadTestextendsThread 2. publicvoidrun() 3. /在這
28、里編寫線程執(zhí)行的主體 4. /dosomething 5. 6. public class ThreadTest extends Thread public void run() / 在這里編寫線程執(zhí)行的主體/ do something這是實現(xiàn)Runnable接口實現(xiàn)多線程的示例: Java代碼 1. publicclassRunnableTestimplementsRunnable 2. publicvoidrun() 3. /在這里編寫線程執(zhí)行的主體 4. /dosomething 5. 6. public class RunnableTest implements Runnable pu
29、blic void run() / 在這里編寫線程執(zhí)行的主體/ do something這兩種實現(xiàn)方式的區(qū)別并不大。繼承Thread類的方式實現(xiàn)起來較為簡單,但是繼承它的類就不能再繼承別的類了,因此也就不能繼承別的類的有用的方法了。而使用是想Runnable接口的方式就不存在這個問題了,而且這種實現(xiàn)方式將線程主體和線程對象本身分離開來,邏輯上也較為清晰,所以推薦大家更多地采用這種方式。 如何啟動線程 我們通過以上兩種方式實現(xiàn)了一個線程之后,線程的實例并沒有被創(chuàng)建,因此它們也并沒有被運行。我們要啟動一個線程,必須調(diào)用方法來啟動它,這個方法就是Thread類的start()方法,而不是run()方
30、法(既不是我們繼承Thread類重寫的run()方法,也不是實現(xiàn)Runnable接口的run()方法)。run()方法中包含的是線程的主體,也就是這個線程被啟動后將要運行的代碼,它跟線程的啟動沒有任何關系。上面兩種實現(xiàn)線程的方式在啟動時會有所不同。 繼承Thread類的啟動方式: Java代碼 1. publicclassThreadStartTest 2. publicstaticvoidmain(Stringargs) 3. /創(chuàng)建一個線程實例 4. ThreadTesttt=newThreadTest(); 5. /啟動線程 6. tt.start(); 7. 8. public cla
31、ss ThreadStartTest public static void main(String args) / 創(chuàng)建一個線程實例ThreadTest tt = new ThreadTest();/ 啟動線程tt.start();實現(xiàn)Runnable接口的啟動方式: Java代碼 1. publicclassRunnableStartTest 2. publicstaticvoidmain(Stringargs) 3. /創(chuàng)建一個線程實例 4. Threadt=newThread(newRunnableTest(); 5. /啟動線程 6. t.start(); 7. 8. public c
32、lass RunnableStartTest public static void main(String args) / 創(chuàng)建一個線程實例Thread t = new Thread(new RunnableTest();/ 啟動線程t.start();實際上這兩種啟動線程的方式原理是一樣的。首先都是調(diào)用本地方法啟動一個線程,其次是在這個線程里執(zhí)行目標對象的run()方法。那么這個目標對象是什么呢?為了弄明白這個問題,我們來看看Thread類的run()方法的實現(xiàn): Java代碼 1. publicvoidrun() 2. if(target!=null) 3. target.run(); 4
33、. 5. public void run() if (target != null) target.run();當我們采用實現(xiàn)Runnable接口的方式來實現(xiàn)線程的情況下,在調(diào)用new Thread(Runnable target)構(gòu)造器時,將實現(xiàn)Runnable接口的類的實例設置成了線程要執(zhí)行的主體所屬的目標對象target,當線程啟動時,這個實例的run()方法就被執(zhí)行了。當我們采用繼承Thread的方式實現(xiàn)線程時,線程的這個run()方法被重寫了,所以當線程啟動時,執(zhí)行的是這個對象自身的run()方法。總結(jié)起來就一句話,線程類有一個Runnable類型的target屬性,它是線程啟動后要
34、執(zhí)行的run()方法所屬的主體,如果我們采用的是繼承Thread類的方式,那么這個target就是線程對象自身,如果我們采用的是實現(xiàn)Runnable接口的方式,那么這個target就是實現(xiàn)了Runnable接口的類的實例。 線程的狀態(tài) 在Java 1.4及以下的版本中,每個線程都具有新建、可運行、阻塞、死亡四種狀態(tài),但是在Java 5.0及以上版本中,線程的狀態(tài)被擴充為新建、可運行、阻塞、等待、定時等待、死亡六種。線程的狀態(tài)完全包含了一個線程從新建到運行,最后到結(jié)束的整個生命周期。線程狀態(tài)的具體信息如下: 1. NEW(新建狀態(tài)、初始化狀態(tài)):線程對象已經(jīng)被創(chuàng)建,但是還沒有被啟動時的狀態(tài)。這段
35、時間就是在我們調(diào)用new命令之后,調(diào)用start()方法之前。 2. RUNNABLE(可運行狀態(tài)、就緒狀態(tài)):在我們調(diào)用了線程的start()方法之后線程所處的狀態(tài)。處于RUNNABLE狀態(tài)的線程在JAVA虛擬機(JVM)上是運行著的,但是它可能還正在等待操作系統(tǒng)分配給它相應的運行資源以得以運行。 3. BLOCKED(阻塞狀態(tài)、被中斷運行):線程正在等待其它的線程釋放同步鎖,以進入一個同步塊或者同步方法繼續(xù)運行;或者它已經(jīng)進入了某個同步塊或同步方法,在運行的過程中它調(diào)用了某個對象繼承自java.lang.Object的wait()方法,正在等待重新返回這個同步塊或同步方法。 4. WAIT
36、ING(等待狀態(tài)):當前線程調(diào)用了java.lang.Object.wait()、java.lang.Thread.join()或者java.util.concurrent.locks.LockSupport.park()三個中的任意一個方法,正在等待另外一個線程執(zhí)行某個操作。比如一個線程調(diào)用了某個對象的wait()方法,正在等待其它線程調(diào)用這個對象的notify()或者notifyAll()(這兩個方法同樣是繼承自Object類)方法來喚醒它;或者一個線程調(diào)用了另一個線程的join()(這個方法屬于Thread類)方法,正在等待這個方法運行結(jié)束。 5. TIMED_WAITING(定時等待狀
37、態(tài)):當前線程調(diào)用了java.lang.Object.wait(long timeout)、java.lang.Thread.join(long millis)、java.util.concurrent.locks.LockSupport.packNanos(long nanos)、java.util.concurrent.locks.LockSupport.packUntil(long deadline)四個方法中的任意一個,進入等待狀態(tài),但是與WAITING狀態(tài)不同的是,它有一個最大等待時間,即使等待的條件仍然沒有滿足,只要到了這個時間它就會自動醒來。 6. TERMINATED(死亡狀態(tài)
38、、終止狀態(tài)):線程完成執(zhí)行后的狀態(tài)。線程執(zhí)行完run()方法中的全部代碼,從該方法中退出,進入TERMINATED狀態(tài)。還有一種情況是run()在運行過程中拋出了一個異常,而這個異常沒有被程序捕獲,導致這個線程異常終止進入TERMINATED狀態(tài)。 在Java5.0及以上版本中,線程的全部六種狀態(tài)都以枚舉類型的形式定義在java.lang.Thread類中了,代碼如下: Java代碼 1. publicenumState 2. NEW, 3. RUNNABLE, 4. BLOCKED, 5. WAITING, 6. TIMED_WAITING, 7. TERMINATED; 8. public
39、 enum State NEW,RUNNABLE,BLOCKED,WAITING,TIMED_WAITING,TERMINATED;sleep()和wait()的區(qū)別 sleep()方法和wait()方法都成產(chǎn)生讓當前運行的線程停止運行的效果,這是它們的共同點。下面我們來詳細說說它們的不同之處。 sleep()方法是本地方法,屬于Thread類,它有兩種定義: Java代碼 1. publicstaticnativevoidsleep(longmillis)throwsInterruptedException; 2. 3. publicstaticvoidsleep(longmillis,in
40、tnanos)throwsInterruptedException 4. /othercode 5. public static native void sleep(long millis) throws InterruptedException;public static void sleep(long millis, int nanos) throws InterruptedException /other code其中的參數(shù)millis代表毫秒數(shù)(千分之一秒),nanos代表納秒數(shù)(十億分之一秒)。這兩個方法都可以讓調(diào)用它的線程沉睡(停止運行)指定的時間,到了這個時間,線程就會自動醒來,
41、變?yōu)榭蛇\行狀態(tài)(RUNNABLE),但這并不表示它馬上就會被運行,因為線程調(diào)度機制恢復線程的運行也需要時間。調(diào)用sleep()方法并不會讓線程釋放它所持有的同步鎖;而且在這期間它也不會阻礙其它線程的運行。上面的連個方法都聲明拋出一個InterruptedException類型的異常,這是因為線程在sleep()期間,有可能被持有它的引用的其它線程調(diào)用它的interrupt()方法而中斷。中斷一個線程會導致一個InterruptedException異常的產(chǎn)生,如果你的程序不捕獲這個異常,線程就會異常終止,進入TERMINATED狀態(tài),如果你的程序捕獲了這個異常,那么程序就會繼續(xù)執(zhí)行catch語
42、句塊(可能還有finally語句塊)以及以后的代碼。 為了更好地理解interrupt()效果,我們來看一下下面這個例子: Java代碼 1. publicclassInterruptTest 2. publicstaticvoidmain(Stringargs) 3. Threadt=newThread() 4. publicvoidrun() 5. try 6. System.out.println(我被執(zhí)行了-在sleep()方法前); 7. /停止運行10分鐘 8. Thread.sleep(1000*60*10); 9. System.out.println(我被執(zhí)行了-在sleep
43、()方法后); 10. catch(InterruptedExceptione) 11. System.out.println(我被執(zhí)行了-在catch語句塊中); 12. 13. System.out.println(我被執(zhí)行了-在try語句塊后); 14. 15. ; 16. /啟動線程 17. t.start(); 18. /在sleep()結(jié)束前中斷它 19. errupt(); 20. 21. public class InterruptTest public static void main(String args) Thread t = new Thread() pub
44、lic void run() try System.out.println(我被執(zhí)行了-在sleep()方法前);/ 停止運行10分鐘Thread.sleep(1000 * 60 * 10);System.out.println(我被執(zhí)行了-在sleep()方法后); catch (InterruptedException e) System.out.println(我被執(zhí)行了-在catch語句塊中);System.out.println(我被執(zhí)行了-在try語句塊后);/ 啟動線程t.start();/ 在sleep()結(jié)束前中斷它errupt();運行結(jié)果: 1. 我被執(zhí)行了-在
45、sleep()方法前 2. 我被執(zhí)行了-在catch語句塊中 3. 我被執(zhí)行了-在try語句塊后 wait()方法也是本地方法,屬于Object類,有三個定義: Java代碼 1. publicfinalvoidwait()throwsInterruptedException 2. /dosomething 3. 4. 5. publicfinalnativevoidwait(longtimeout)throwsInterruptedException; 6. 7. publicfinalvoidwait(longtimeout,intnanos)throwsInterruptedExcept
46、ion 8. /dosomething 9. public final void wait() throws InterruptedException /do somethingpublic final native void wait(long timeout) throws InterruptedException;public final void wait(long timeout, int nanos) throws InterruptedException /do somethingwari()和wait(long timeout,int nanos)方法都是基于wait(long timeout)方法實現(xiàn)的。同樣地,timeout代表毫秒數(shù),nanos代表納秒數(shù)。當調(diào)用了某個對象的wait()方法時,當前運行的線程就會轉(zhuǎn)入等待狀態(tài)(WAITING),等待別的線程再次調(diào)用這個對象的notify()或者notifyAll()方法(這兩個方法也是本地方法)喚醒它,或者到了指定的最大等待時間,線程自動醒來。如果線程擁有某個或某些對象的同步鎖,那么在調(diào)用了wait()后,這個線程就會釋放它持有的所有同步資源,而不限于這個被調(diào)用了wait()方法的對象。wait()方法同樣會被Thread類的interrupt()方法中斷,并產(chǎn)生一個InterruptedEx
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
- 6. 下載文件中如有侵權(quán)或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- PB-22-N-5-Hydroxypentyl-3-carboxyindole-metabolite-生命科學試劑-MCE-1773
- L-Glutamic-acid-ammonium-生命科學試劑-MCE-7975
- 1-Octadecyl-lysophosphatidic-acid-PA-O-18-0-0-0-生命科學試劑-MCE-8369
- 2025年度績效合同簽訂與履行指南
- 二零二五年度未簽合同員工勞動仲裁應對措施及賠償協(xié)議
- 二零二五年度物業(yè)與業(yè)主之間綠化賠償合作協(xié)議
- 2025年度煙酒店員工培訓與職業(yè)發(fā)展合同
- 柴油發(fā)電機組技術協(xié)議
- 施工日志填寫樣本防雷工程施工
- 小學語文人教一年級上冊識字2《日月明》教學設計
- 充電樁知識培訓課件
- 2025年七年級下冊道德與法治主要知識點
- 2025年交通運輸部長江口航道管理局招聘4人歷年高頻重點提升(共500題)附帶答案詳解
- 老年髖部骨折患者圍術期下肢深靜脈血栓基礎預防專家共識(2024版)解讀
- 廣東省廣州市2025屆高三上學期12月調(diào)研測試(零模)英語 含解析
- 偏癱足內(nèi)翻的治療
- 藥企質(zhì)量主管競聘
- 信息對抗與認知戰(zhàn)研究-洞察分析
- 心腦血管疾病預防課件
- 手術室專科護士工作總結(jié)匯報
- 2025屆高三聽力技巧指導-預讀、預測
評論
0/150
提交評論