java線程的中斷和同步問(wèn)題的實(shí)現(xiàn)
1、自動(dòng)終斷【完成】:一個(gè)線程完成執(zhí)行后(即run方法執(zhí)行完畢),不能再次運(yùn)行 。
2、手動(dòng)中斷:
stop( ) —— 已過(guò)時(shí),基本不用。(不安全,就像是突然停電)
interrupt( ) ——此方法只是改變中斷狀態(tài),不會(huì)中斷一個(gè)正在運(yùn)行的線程。比如:如果當(dāng)前線程是阻塞狀態(tài),那么就結(jié)束阻塞狀態(tài)
3、可通過(guò)使用一個(gè)標(biāo)志指示 run 方法退出,從而終止線程(推薦使用)
使用場(chǎng)景
- 點(diǎn)擊某個(gè)桌面應(yīng)用中的取消按鈕時(shí);
- 某個(gè)操作超過(guò)了一定的執(zhí)行時(shí)間限制需要中止時(shí);
- 多個(gè)線程做相同的事情,只要一個(gè)線程成功其它線程都可以取消時(shí);
- 一組線程中的一個(gè)或多個(gè)出現(xiàn)錯(cuò)誤導(dǎo)致整組都無(wú)法繼續(xù)時(shí);
- 當(dāng)一個(gè)應(yīng)用或服務(wù)需要停止時(shí)
- interrupt( )方法說(shuō)明:interrupt()方法只是改變中斷狀態(tài),不會(huì)中斷一個(gè)正在運(yùn)行的線程。這一方法實(shí)際完成的是,給受阻塞的線程發(fā)出一個(gè)中斷信號(hào),這樣受阻線程檢查到中斷標(biāo)識(shí),就得以退出阻塞的狀態(tài)。更確切的說(shuō),如果線程被Object.wait, Thread.join和Thread.sleep三種方法之一阻塞,此時(shí)調(diào)用該線程的interrupt()方法,那么該線程將拋出一個(gè) InterruptedException中斷異常(該線程必須事先預(yù)備好處理此異常),從而提早地終結(jié)被阻塞狀態(tài)。如果線程沒(méi)有被阻塞,這時(shí)調(diào)用 interrupt()將不起作用,直到執(zhí)行到wait(),sleep(),join()時(shí),才馬上會(huì)拋出 InterruptedException。
線程同步問(wèn)題

同步解決方案synchronized
1.在java語(yǔ)言中,引入了同步鎖的概念,每個(gè)對(duì)象都有一個(gè)與之關(guān)聯(lián)的內(nèi)部鎖(排他鎖),用以保證共享數(shù)據(jù)的安全性問(wèn)題。
2.關(guān)鍵詞synchronized用來(lái)給某個(gè)方法或某段代碼加上一個(gè)同步鎖。
3.當(dāng)調(diào)用者調(diào)用此方法時(shí),必須獲得這把鎖才可以調(diào)用。
4.當(dāng)某個(gè)調(diào)用者獲得這把鎖之后,其他調(diào)用者就無(wú)法獲得了。
5.當(dāng)調(diào)用結(jié)束后,調(diào)用者釋放這把鎖,此時(shí)其他調(diào)用者才可以獲得。
6.這個(gè)機(jī)制保障了某個(gè)同步方法同時(shí)只能有一個(gè)調(diào)用者
鎖定方法
public class Account {
private int balance = 1000;
public synchronized void qu(){ // 同步方法
if(balance>=1000){
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
balance -= 1000;
System.out.println("取了1000元,balance = " + balance);
}
}
}鎖定代碼塊
public class Account {
private int balance = 1000;
public void qu(){
System.out.println("Account.qu");
synchronized( "this" ){ // 同步塊
if(balance>=1000){
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
balance -= 1000;
System.out.println("取了1000元,balance = " + balance);
}
}
}
}死鎖

線程同步的第二種解決方案 wait() notify()
生產(chǎn)者-消費(fèi)者(producer-consumer)問(wèn)題,也稱作有界緩沖區(qū)(bounded-buffer)問(wèn)題,兩個(gè)線程共享一個(gè)公共的固定大小的緩沖區(qū)。其中一個(gè)是生產(chǎn)者,用于將消息放入緩沖區(qū);另外一個(gè)是消費(fèi)者,用于從緩沖區(qū)中取出消息。問(wèn)題出現(xiàn)在當(dāng)緩沖區(qū)已經(jīng)滿了,而此時(shí)生產(chǎn)者還想向其中放入一個(gè)新的數(shù)據(jù)項(xiàng)的情形,其解決方法是讓生產(chǎn)者此時(shí)進(jìn)行休眠,等待消費(fèi)者從緩沖區(qū)中取走了一個(gè)或者多個(gè)數(shù)據(jù)后再去喚醒它
package test06;
//倉(cāng)庫(kù)(有界緩沖區(qū))
class Storage{
private int count = 0;
public synchronized void set(){
if(count>=5){
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
count++;
System.out.println("生產(chǎn)了一個(gè),倉(cāng)庫(kù)中有:" + count);
this.notify();
}
public synchronized void get(){
if(count<=0){
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
count--;
System.out.println("消費(fèi)了一個(gè),倉(cāng)庫(kù)中有:" + count);
this.notify();
}
}
//生產(chǎn)者
class Producer extends Thread{
private Storage storage;
public Producer(Storage storage){
this.storage = storage;
}
public void run(){
for(int i=0;i<50;i++){
this.storage.set();
}
}
}
//消費(fèi)者
class Customer extends Thread{
private Storage storage;
public Customer(Storage storage){
this.storage = storage;
}
public void run(){
for(int i=0;i<50;i++){
this.storage.get();
}
}
}
public class Test2 {
public static void main(String[] args) {
Storage storage = new Storage();
Producer producer = new Producer(storage);
Customer customer = new Customer(storage);
customer.start();
producer.start();
}
}到此這篇關(guān)于java線程的中斷和同步問(wèn)題的實(shí)現(xiàn)的文章就介紹到這了,更多相關(guān)java線程中斷和同步內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Java-文件File簡(jiǎn)單實(shí)用方法(分享)
下面小編就為大家?guī)?lái)一篇Java-文件File簡(jiǎn)單實(shí)用方法(分享)。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-08-08
SpringSecurity數(shù)據(jù)庫(kù)進(jìn)行認(rèn)證和授權(quán)的使用
本文主要介紹了用戶的賬號(hào)、密碼以及角色信息在數(shù)據(jù)庫(kù)中的認(rèn)證和授權(quán),文中通過(guò)示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-08-08
java 使用簡(jiǎn)單的demo實(shí)例告訴你優(yōu)化算法的強(qiáng)大
本篇文章介紹了,在java中使用簡(jiǎn)單的demo實(shí)例告訴你優(yōu)化算法的強(qiáng)大。需要的朋友參考下2013-05-05
Docker 部署 SpringBoot 項(xiàng)目整合 Redis 鏡像做訪問(wèn)計(jì)數(shù)示例代碼
這篇文章主要介紹了Docker 部署 SpringBoot 項(xiàng)目整合 Redis 鏡像做訪問(wèn)計(jì)數(shù)Demo,本文給大家介紹的非常詳細(xì),具有參考借鑒價(jià)值,需要的朋友可以參考下2018-01-01
Spring如何使用三級(jí)緩存解決循環(huán)依賴
在Spring框架中,循環(huán)依賴是指兩個(gè)或多個(gè)Bean相互依賴,形成閉環(huán),導(dǎo)致無(wú)法完成初始化,此問(wèn)題僅存在于單例Bean中,而原型Bean會(huì)拋出異常,Spring通過(guò)三級(jí)緩存及提前暴露策略解決循環(huán)依賴:一級(jí)緩存存放完全初始化的Bean2024-11-11
SpringBoot2.x 整合Spring-Session實(shí)現(xiàn)Session共享功能
這篇文章主要介紹了SpringBoot2.x 整合Spring-Session實(shí)現(xiàn)Session共享功能,本文給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2019-07-07

