亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Java基礎(chǔ):徹底搞懂java多線程

 更新時(shí)間:2021年08月26日 10:36:28   作者:xufei5789651  
篇文章主要介紹了Java多線程的相關(guān)資料,幫助大家更好的理解和學(xué)習(xí)Java線程相關(guān)知識(shí),感興趣的朋友可以了解下,希望能給你帶來(lái)幫助

進(jìn)程與線程

進(jìn)程

進(jìn)程是操作系統(tǒng)結(jié)構(gòu)的基礎(chǔ),是程序在一個(gè)數(shù)據(jù)集合上運(yùn)行的過(guò)程,是系統(tǒng)進(jìn)行資源分配和調(diào)度的基本單位。進(jìn)程可以被看作程序的實(shí)體,同樣,它也是程序的容器。

線程

線程是操作系統(tǒng)調(diào)度的最小單元,也叫作輕量級(jí)進(jìn)程。在一個(gè)進(jìn)程中可以創(chuàng)建多個(gè)線程,這些線程都擁有各自的計(jì)數(shù)器、堆棧和局部變量等屬性。

使用多線程的優(yōu)勢(shì)

  • 使用多線程可以減少程序的響應(yīng)時(shí)間

如果某個(gè)操作很耗時(shí),或者陷入長(zhǎng)時(shí)間的等待,此時(shí)程序?qū)⒉粫?huì)響應(yīng)鼠標(biāo)和鍵盤(pán)等的操作,使用多線程后可以把這個(gè)耗時(shí)的操作分配到一個(gè)單獨(dú)的線程中執(zhí)行,從而使程序具備了更好的交互性。

  • 與進(jìn)程相對(duì),線程創(chuàng)建和切換開(kāi)銷(xiāo)更小,同時(shí)多線程在數(shù)據(jù)共享方面效率非常高。
  • 多CPU 或者多核計(jì)算機(jī)本身就具備執(zhí)行多線程的能力。

如果使用單個(gè)線程,將無(wú)法重復(fù)利用計(jì)算機(jī)資源,這會(huì)造成資源的巨大浪費(fèi)。在多CPU計(jì)算機(jī)中使用多線程能提高CPU的利用率。

  • 使用多線程能簡(jiǎn)化程序的結(jié)構(gòu),使程序便于理解和維護(hù)。

線程的狀態(tài)

  • New

新創(chuàng)建狀態(tài)。線程被創(chuàng)建,還沒(méi)有調(diào)用start方法,在線程運(yùn)行之前還有一些基礎(chǔ)工作要做。

  • Runnable

可運(yùn)行狀態(tài)。一旦調(diào)用start方法,線程就處于Runnable 狀態(tài)。一個(gè)可運(yùn)行的線程可能正在運(yùn)行也可能沒(méi)有運(yùn)行,這取決于操作系統(tǒng)給線程提供運(yùn)行的時(shí)間。

  • Blocked

阻塞狀態(tài)。表示線程被鎖阻塞,它暫時(shí)不活動(dòng)。

  • Waiting

等待狀態(tài)。線程暫時(shí)不活動(dòng),并且不運(yùn)行任何代碼,這消耗最少資源,直到線程調(diào)度器重新激活它。

  • Timed waiting

超時(shí)等待狀態(tài)。和等待不同的是,它是可以在指定的時(shí)間自行返回的。

  • Terminated

終止?fàn)顟B(tài)。表示當(dāng)前線程已經(jīng)執(zhí)行完畢。導(dǎo)致線程終止有兩種情況:(1)run方法執(zhí)行完畢正常退出;(2)因?yàn)橐粋€(gè)沒(méi)有捕獲取得異常而終止了run 方法,導(dǎo)致線程進(jìn)入終止?fàn)顟B(tài)。

在這里插入圖片描述

線程創(chuàng)建后,調(diào)用Thead的start方法,開(kāi)始進(jìn)入運(yùn)行狀態(tài),當(dāng)線程執(zhí)行wait方法后,線程進(jìn)入等待狀態(tài),進(jìn)入等待狀態(tài)的線程需要其他線程通知才能返回運(yùn)行狀態(tài)。超時(shí)等待相當(dāng)于在等待狀態(tài)加上了時(shí)間限制,如果超過(guò)時(shí)間限制,則線程返回運(yùn)行狀態(tài)。當(dāng)線程調(diào)用到同步方法時(shí),如果線程沒(méi)有獲得鎖則進(jìn)入阻塞狀態(tài),當(dāng)阻塞狀態(tài)的線程獲取到鎖時(shí)則重新回到運(yùn)行狀態(tài)。當(dāng)線程執(zhí)行完畢或者遇到意外異常終止時(shí),都會(huì)進(jìn)入終止?fàn)顟B(tài)。

創(chuàng)建線程

  • 繼承Thread類(lèi),重寫(xiě)run()方法
    public class ThreadExample2 extends Thread{
    	public static void main(String[] args) {
    		Thread mThread=new ThreadExample2();
    		mThread.start();
    	}
    	@Override
    	public void run() {
    		 System.out.print("thread excute");		
    	}
    }
    
  • 實(shí)現(xiàn)Runnable接口,并實(shí)現(xiàn)該接口的Run()方法 (推薦)
    public class ThreadExample {
    	public static void main(String[] args) {
          ExRunnable runnable=new ExRunnable();
          Thread mThread=new Thread(runnable);
    	  mThread.start();
    	}
    }
    public class ExRunnable implements Runnable{
    	@Override
    	public void run() {
            System.out.print("thread excute");		
    	}
    }
    
  • 實(shí)現(xiàn)Callable接口,重寫(xiě)call()方法

Callable接口是屬于Executor框架中的功能類(lèi)。Callable可以在任務(wù)接受后提供一個(gè)返回值,Runnable無(wú)法提供這個(gè)功能。

  • Callable中的call()方法可以拋出異常,而Runnable的run()方法不能拋出異常。
  • 運(yùn)行Callable可以拿到一個(gè)Future對(duì)象,F(xiàn)uture對(duì)象表示異步計(jì)算的結(jié)果,它提供了檢查計(jì)算是否完成的方法。
  • 由于線程屬于異步計(jì)算模型,因此無(wú)法從別的線程中得到函數(shù)的返回值,在這種情況下就可以使用Future來(lái)監(jiān)視目標(biāo)線程調(diào)用call()方法的情況。但調(diào)用Future的get()方法以獲取結(jié)果時(shí),當(dāng)前線程就會(huì)阻塞,直到call()方法返回結(jié)果。
public class ThreadExample {
	public static void main(String[] args) {
	  ExCallable mCallable=new ExCallable();
	  ExecutorService mExecutorService=Executors.newSingleThreadExecutor();
	  Future<String> mFuture=mExecutorService.submit(mCallable);
	  try {
		System.out.println(mFuture.get());
	  } catch (Exception e) {
		e.printStackTrace();
	  }
	}
}
public class ExCallable implements Callable<String> {
	@Override
	public String call() throws Exception {
		// TODO Auto-generated method stub
		return "thread excute";
	}
}

線程中斷

當(dāng)線程的run 方法執(zhí)行完畢,或者在方法中出現(xiàn)沒(méi)有捕獲的異常時(shí),線程將終止。interrupt方法可以用來(lái)請(qǐng)求中斷線程。當(dāng)一個(gè)線程調(diào)用interrupt方法時(shí),線程的中斷標(biāo)識(shí)位為true,線程會(huì)不時(shí)地檢測(cè)這個(gè)中斷標(biāo)識(shí)位,以判斷線程是否應(yīng)該被中斷。

// 判斷線程是否被中斷
Thread.currentThread().isInterrupted();

拋出InterruptedException 異常后,兩種處理方法:

void task(){
     ....
     try{
        sleep(50)
     }catch(InterruptedException e){
        Thread.currentThread().interrupted(); 
     }
 }

在catch子句中,調(diào)用Thread.currentThread().interrupted()來(lái)設(shè)置中斷狀態(tài)(因?yàn)閽伋霎惓:笾袛鄻?biāo)識(shí)位會(huì)復(fù)位,即重新設(shè)置為false),讓外界通過(guò)Thread.currentThread().isInterrupted() 來(lái)決定是否終止還是繼續(xù)下去。

void task() throw InterrupetedException{
     sleep(50); 
  }

不用try來(lái)捕獲異常,讓方法直接拋出,這樣調(diào)用者可以捕獲這個(gè)異常。

中斷線程Example

public class StopExampleThread {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		try {
			InterruptedRunnable mRunnable=new InterruptedRunnable();
			Thread thread=new Thread(mRunnable,"threadDemo");
			thread.start();
			TimeUnit.MILLISECONDS.sleep(10);
			thread.interrupt();
		} catch (InterruptedException e) {
			// 拋出InterruptedException后中斷標(biāo)志被清除
			// 再次調(diào)用interrupt恢復(fù)中斷
			Thread.currentThread().interrupt();
		}
	}
	static class InterruptedRunnable implements Runnable{
		int i=0;
		@Override
		public void run() {
			// TODO Auto-generated method stub
			while(!Thread.currentThread().isInterrupted()) {
				i++;
				System.out.println("i="+i);
			}
			System.out.println("stop");			
		}
	}

總結(jié)

  • 如果一個(gè)線程處于阻塞狀態(tài),線程在檢查中斷標(biāo)識(shí)位時(shí),如果發(fā)現(xiàn)中斷標(biāo)識(shí)位為true,則會(huì)在阻塞方法調(diào)用處拋出InterruptedException 異常,并且在拋出異常前將線程的中斷標(biāo)識(shí)位復(fù)位,即重新設(shè)置為false。
  • 被中斷的線程不一定會(huì)終止,中斷線程是為了引起線程的注意,被中斷的線程可以決定如何去響應(yīng)中斷。如果是比較重要的線程則不會(huì)理會(huì)中斷,而大部分情況則是線程會(huì)將中斷作為一個(gè)終止的請(qǐng)求。

本篇文章就到這里了,希望能給你帶來(lái)幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!

相關(guān)文章

  • java集合類(lèi)源碼分析之Set詳解

    java集合類(lèi)源碼分析之Set詳解

    下面小編就為大家?guī)?lái)一篇java集合類(lèi)源碼分析之Set詳解。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2017-10-10
  • 詳解Mybatis的二級(jí)緩存配置

    詳解Mybatis的二級(jí)緩存配置

    這篇文章主要介紹了Mybatis的二級(jí)緩存配置的相關(guān)資料,需要的朋友可以參考下
    2017-05-05
  • java之向linux文件夾下寫(xiě)文件無(wú)權(quán)限的問(wèn)題

    java之向linux文件夾下寫(xiě)文件無(wú)權(quán)限的問(wèn)題

    這篇文章主要介紹了java之向linux文件夾下寫(xiě)文件無(wú)權(quán)限的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-09-09
  • JavaWeb實(shí)現(xiàn)自動(dòng)登錄功能

    JavaWeb實(shí)現(xiàn)自動(dòng)登錄功能

    這篇文章主要為大家詳細(xì)介紹了JavaWeb實(shí)現(xiàn)自動(dòng)登錄功能,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-08-08
  • JAVA編程實(shí)現(xiàn)TCP網(wǎng)絡(luò)通訊的方法示例

    JAVA編程實(shí)現(xiàn)TCP網(wǎng)絡(luò)通訊的方法示例

    這篇文章主要介紹了JAVA編程實(shí)現(xiàn)TCP網(wǎng)絡(luò)通訊的方法,簡(jiǎn)單說(shuō)明了TCP通訊的原理并結(jié)合具體實(shí)例形式分析了java實(shí)現(xiàn)TCP通訊的步驟與相關(guān)操作技巧,需要的朋友可以參考下
    2017-08-08
  • SpringSecurity 自定義表單登錄的實(shí)現(xiàn)

    SpringSecurity 自定義表單登錄的實(shí)現(xiàn)

    這篇文章主要介紹了SpringSecurity 自定義表單登錄的實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-01-01
  • SpringAOP切點(diǎn)函數(shù)實(shí)現(xiàn)原理詳解

    SpringAOP切點(diǎn)函數(shù)實(shí)現(xiàn)原理詳解

    這篇文章主要介紹了SpringAOP切點(diǎn)函數(shù)實(shí)現(xiàn)原理詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-05-05
  • Java實(shí)現(xiàn)紅黑樹(shù)(平衡二叉樹(shù))的詳細(xì)過(guò)程

    Java實(shí)現(xiàn)紅黑樹(shù)(平衡二叉樹(shù))的詳細(xì)過(guò)程

    紅黑樹(shù)接近平衡的二叉樹(shù),插入,刪除函數(shù)跟平衡二叉樹(shù)一樣,只是平衡函數(shù)不同,下面這篇文章主要給大家介紹了關(guān)于Java實(shí)現(xiàn)紅黑樹(shù)(平衡二叉樹(shù))的相關(guān)資料,需要的朋友可以參考下
    2021-10-10
  • 利用JDBC的PrepareStatement打印真實(shí)SQL的方法詳解

    利用JDBC的PrepareStatement打印真實(shí)SQL的方法詳解

    PreparedStatement是預(yù)編譯的,對(duì)于批量處理可以大大提高效率. 也叫JDBC存儲(chǔ)過(guò)程,下面這篇文章主要給大家介紹了關(guān)于利用JDBC的PrepareStatement打印真實(shí)SQL的方法,需要的朋友可以參考借鑒,下面來(lái)一起看看吧。
    2017-07-07
  • 面試官:java ThreadLocal真的會(huì)造成內(nèi)存泄露嗎

    面試官:java ThreadLocal真的會(huì)造成內(nèi)存泄露嗎

    ThreadLocal,java面試過(guò)程中的“釘子戶”,在網(wǎng)上也充斥著各種有關(guān)ThreadLocal內(nèi)存泄露的問(wèn)題,本文換個(gè)角度,先思考ThreadLocal體系中的ThreadLocalMap為什么要設(shè)計(jì)成弱引用
    2021-08-08

最新評(píng)論