最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

java并發(fā)編程中實(shí)現(xiàn)可見(jiàn)性的四種可行方案解析

 更新時(shí)間:2023年08月07日 09:04:53   作者:鍵盤(pán)林  
這篇文章主要介紹了java并發(fā)編程中實(shí)現(xiàn)可見(jiàn)性的四種可行方案解析,使用關(guān)鍵字volatile和使用鎖(如synchronized關(guān)鍵字或者java.util.concurrent包中的鎖)來(lái)確保對(duì)共享變量的修改在多線程環(huán)境中能夠正確地被其他線程所觀察到,需要的朋友可以參考下

在方法或者變量已經(jīng)同步的情況下,還會(huì)出現(xiàn)什么問(wèn)題嗎?

多線程編程主要學(xué)的就是"互斥"和"可見(jiàn)","互斥"指的就是就是同步,而"可見(jiàn)"想必很多人還沒(méi)有理解.

舉個(gè)例子:

MyVolatile.java:

package cn.mxl.test.wr;
public class MyVolatile {
	private  int a=0;
	public   void write() throws InterruptedException {
		a++;
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
	public   void read() throws InterruptedException {
		while(a==0) {
//			Thread.sleep(1);
//			System.out.println(a);
		}
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
}

MyRead.java:

package cn.mxl.test.wr;
public class MyRead implements Runnable{
	private MyVolatile task;
	public MyRead(MyVolatile task) {
		// TODO Auto-generated constructor stub
		this.task=task;
	}
	@Override
	public void run() {
		// TODO Auto-generated method stub
		try {
			task.read();
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}

MyWrite.java:

package cn.mxl.test.wr;
public class MyWrite implements Runnable{
	private MyVolatile task;
	public MyWrite(MyVolatile task) {
		// TODO Auto-generated constructor stub
		this.task=task;
	}
	@Override
	public void run() {
		// TODO Auto-generated method stub
		try {
			task.write();
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}

Run.java:

package cn.mxl.test.wr;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.locks.ReentrantLock;
public class Run {
	public static void main(String[] args) throws Exception, ExecutionException {
		MyVolatile task=new MyVolatile();
		MyWrite mt1=new MyWrite(task);
		MyRead mt2=new MyRead(task);
		Thread tW=new Thread(mt1,"Write");
		Thread tR=new Thread(mt2,"Read");
		tR.start();
		Thread.sleep(2000);
		tW.start();
	}
}

運(yùn)行結(jié)果:

Read線程一直處于a==0中是為什么呢?

因?yàn)楫?dāng)Read線程 先開(kāi)始線程的時(shí)候,加載主內(nèi)存中的數(shù)據(jù)放到自己的私有內(nèi)存中,在程序執(zhí)行過(guò)程中為了提高效率,它就只讀自己私有內(nèi)存中的數(shù)據(jù),不會(huì)再去讀主內(nèi)存中的共享數(shù)據(jù),在這個(gè)過(guò)程中,主內(nèi)存對(duì)于該線程來(lái)說(shuō),只寫(xiě)不讀,也就是說(shuō)將自己修改的變量值存放到主內(nèi)存中,但是自己不去讀主內(nèi)存的數(shù)據(jù);所以說(shuō),在Read線程執(zhí)行到while語(yǔ)句一直循環(huán)的時(shí)候,即使Write線程修改a==1值了,Read線程還是之前a==0的值,一直跳不出循環(huán);

解決辦法-->可見(jiàn)性,讓Read線程讀a變量的時(shí)候去主內(nèi)存(共享數(shù)據(jù))中讀取:

volatiel關(guān)鍵字的使用:

MyVolatile.java:

package cn.mxl.test.wr;
public class MyVolatile {
	private volatile  int a=0;
	public   void write() throws InterruptedException {
		a++;
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
	public   void read() throws InterruptedException {
		while(a==0) {
//			Thread.sleep(1);
//			System.out.println(a);
		}
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
}

結(jié)果:

其實(shí)在這個(gè)過(guò)程中,我遇到了一些有趣的事情,可見(jiàn)性這東西,其實(shí)還有三個(gè)東西可以實(shí)現(xiàn):

第一個(gè)-->Thread.sleep():

MyVolatile.java(取消sleep的注解):

package cn.mxl.test.wr;
public class MyVolatile {
	private   int a=0;
	public   void write() throws InterruptedException {
		a++;
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
	public   void read() throws InterruptedException {
		while(a==0) {
			Thread.sleep(1);
//			System.out.println(a);
		}
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
}

 結(jié)果:

第二個(gè)是system.out.println():

MyVolatile.java:

package cn.mxl.test.wr;
public class MyVolatile {
	private   int a=0;
	public   void write() throws InterruptedException {
		a++;
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
	public   void read() throws InterruptedException {
		while(a==0) {
//			Thread.sleep(1);
			System.out.println(a);
		}
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
}

 結(jié)果:

 第三個(gè)atomic:

MyVolatile.java:

package cn.mxl.test.wr.atomic;
import java.util.concurrent.atomic.AtomicInteger;
public class MyVolatile {
	private   AtomicInteger a=new AtomicInteger();
	public   void write() throws InterruptedException {
		a.incrementAndGet();
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
	public   void read() throws InterruptedException {
		while(a.get()==0) {
//			Thread.sleep(1);
//			System.out.println(a);
		}
		System.out.println("當(dāng)前線程:"+Thread.currentThread().getName());
		System.out.println(a);
	}
}

結(jié)果:

到此這篇關(guān)于java并發(fā)編程中實(shí)現(xiàn)可見(jiàn)性的四種可行方案解析的文章就介紹到這了,更多相關(guān)java實(shí)現(xiàn)可見(jiàn)性內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Spring整合Mybatis 掃描注解創(chuàng)建Bean報(bào)錯(cuò)的解決方案

    Spring整合Mybatis 掃描注解創(chuàng)建Bean報(bào)錯(cuò)的解決方案

    這篇文章主要介紹了Spring 整合Mybatis 掃描注解創(chuàng)建Bean報(bào)錯(cuò)的解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-10-10
  • SpringBoot配置攔截器的示例

    SpringBoot配置攔截器的示例

    這篇文章主要介紹了SpringBoot配置攔截器的示例,幫助大家更好的理解和使用springboot框架,感興趣的朋友可以了解下
    2020-11-11
  • 深入解析Java的設(shè)計(jì)模式編程中單例模式的使用

    深入解析Java的設(shè)計(jì)模式編程中單例模式的使用

    這篇文章主要介紹了深入解析Java的設(shè)計(jì)模式編程中單例模式的使用,一般來(lái)說(shuō)將單例模式分為餓漢式單例和懶漢式單例,需要的朋友可以參考下
    2016-02-02
  • Spring中使用自定義ThreadLocal存儲(chǔ)導(dǎo)致的坑及解決

    Spring中使用自定義ThreadLocal存儲(chǔ)導(dǎo)致的坑及解決

    這篇文章主要介紹了Spring中使用自定義ThreadLocal存儲(chǔ)導(dǎo)致的坑及解決,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-12-12
  • Spring AOP AspectJ使用及配置過(guò)程解析

    Spring AOP AspectJ使用及配置過(guò)程解析

    這篇文章主要介紹了Spring AOP AspectJ使用及配置過(guò)程解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-01-01
  • Java中的代理模式詳解及實(shí)例代碼

    Java中的代理模式詳解及實(shí)例代碼

    這篇文章主要介紹了Java中的代理模式詳解及實(shí)例代碼的相關(guān)資料,這里附有實(shí)例代碼,需要的朋友可以參考下
    2017-02-02
  • SpringBoot攔截器的使用介紹

    SpringBoot攔截器的使用介紹

    大家好,本篇文章主要講的是SpringBoot攔截器的使用介紹,感興趣的同學(xué)趕快來(lái)看一看吧,對(duì)你有幫助的話記得收藏一下
    2022-01-01
  • Java+opencv3.2.0實(shí)現(xiàn)模板匹配

    Java+opencv3.2.0實(shí)現(xiàn)模板匹配

    這篇文章主要為大家詳細(xì)介紹了Java+opencv3.2.0實(shí)現(xiàn)模板匹配的相關(guān)資料,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-02-02
  • 使用Feign動(dòng)態(tài)設(shè)置header和原理分析

    使用Feign動(dòng)態(tài)設(shè)置header和原理分析

    這篇文章主要介紹了使用Feign動(dòng)態(tài)設(shè)置header和原理分析,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-03-03
  • JDK8安裝與配置實(shí)踐超詳細(xì)指南

    JDK8安裝與配置實(shí)踐超詳細(xì)指南

    本文詳細(xì)介紹了在Windows?64位系統(tǒng)上安裝和配置JDK8的步驟,包括JDK8下載、環(huán)境變量設(shè)置及安裝驗(yàn)證,同時(shí)提供了JDK8新特性如Lambda表達(dá)式、StreamAPI等的概覽,旨在幫助Java開(kāi)發(fā)者有效利用JDK8新特性進(jìn)行開(kāi)發(fā),需要的朋友可以參考下
    2024-10-10

最新評(píng)論

明水县| 丹巴县| 理塘县| 新源县| 罗田县| 寿宁县| 天镇县| 冷水江市| 龙泉市| 江城| 南京市| 阿合奇县| 平凉市| 丹阳市| 岳池县| 广宗县| 泉州市| 贵州省| 丹凤县| 石屏县| 肃宁县| 遵义市| 吴川市| 恩施市| 洛阳市| 阿勒泰市| 英超| 隆子县| 武功县| 兴城市| 辽宁省| 曲麻莱县| 黑河市| 华宁县| 四川省| 仁化县| 阿城市| 斗六市| 金溪县| 罗源县| 陵川县|