当前位置: 首页 > wzjs >正文

php购物网站设计代码app拉新推广赚佣金

php购物网站设计代码,app拉新推广赚佣金,wordpress discuz用户,网站建设内部需求调查表各位看官,大家早安午安晚安呀~~~ 如果您觉得这篇文章对您有帮助的话 欢迎您一键三连,小编尽全力做到更好 欢迎您分享给更多人哦 今天我们来学习:wait和notify : 避免线程饿死(以及votile内存可见性和指令重排序问题) …

各位看官,大家早安午安晚安呀~~~

如果您觉得这篇文章对您有帮助的话

欢迎您一键三连,小编尽全力做到更好
欢迎您分享给更多人哦

今天我们来学习:wait和notify : 避免线程饿死(以及votile内存可见性和指令重排序问题)

目录

4.volatile

4.1.保证内存可见性

4.2.:指令重排序问题(我们放到下一篇博客来讲解)

5.wait,notify

5.1.wait方法的使用

5.2.notify方法的使用

6.wait和notify可以避免线程饿死


4.volatile

volatile的两个作用(其实都是不让编译器做出多余的优化,对我们的程序产生bug)

1.保证内存可见性

2.解决指令重排序问题

4.1.保证内存可见性

序言:

计算机运行的程序往往要访问数据,这些依赖的数据一般都被读取到了内存里面(譬如我们定义的一个变量就是在内存里面)

就譬如count++;cpu先把count读到cpu寄存器里面再进行++;

但是!  cpu其他的操作都很快,但是读内存就比较慢(读硬盘更慢,快慢都是相对的)

因此,为了提高效率编译器就会做出优化,把一些要读内存的操作优化成读寄存器。减少读内存的次数,就提高了整体程序的效率~~

public class Demo1 {private static int isQuit = 0;public static void main(String[] args) {Thread t1 = new Thread(() ->{while(isQuit == 0){// 一直循环啥也不不干}System.out.println("t1 退出");});Thread t2 = new Thread(()->{System.out.println(" 请输入isQuit的值");Scanner scanner = new Scanner(System.in);isQuit = scanner.nextInt(); // 输入不为0的值,使t1线程结束});t1.start();t2.start();}
}

我们发现我们明明输入非0值但是t1线程就是没结束为什么呢?

所以说volatile就是一个优化方法,我们给isQuit前面用volatile修饰就可以避免这样的问题了

       在多线程环境下,编译器对于是否要进行这样的优化,判定不一定准.这个时候就需要程序猿通过 volatile 关键字,告诉编译器,这个情况不用优化!!!优化,是算的快了,但是算的不准了)

 总之:编译器,也不是万能的.也会有一些自己短板的地方.此时就需要程序猿进行补充了.
只需要给 isQuit加上 volatile 关键字修饰,此时编译器自然就会禁止上述优化过程。

还有另一种方式,也可以避免这样的问题(再加上一个时间更长的操作,让读内存不那么慢了(相对来说)哈哈)

public class Demo1 {private static int isQuit = 0;public static void main(String[] args) {Thread t1 = new Thread(() ->{while(isQuit == 0){// 一直循环啥也不不干try {   //就多加了一个sleepThread.sleep(1000);} catch (InterruptedException e) {throw new RuntimeException(e);}}System.out.println("t1 退出");});Thread t2 = new Thread(()->{System.out.println(" 请输入isQuit的值");Scanner scanner = new Scanner(System.in);isQuit = scanner.nextInt(); // 输入不为0的值,使t1线程结束});t1.start();t2.start();}
}

此时没加 volatile, 但是给循环里加了个 slee

线程是可以退出了
加了 sleep 之后, while 循环执行速度就慢了.由于次数少了,load (读内存)操作的开销,就不大了.因此,优化也就没必要进行了.
没有触发 load的优化,也就没有触发内存可见性问题了.
到底啥时候代码有优化,啥时候没有?也说不清楚,但是使用 volatile 还是更靠谱的选择!!

4.2.:指令重排序问题(我们放到下一篇博客来讲解)

5.wait,notify

每个线程都是独立的执行流

想法:

由于线程之间是抢占式执行的, 因此线程之间执行的先后顺序难以预知.(join是决定了线程结束的先后顺序)
但是实际开发中有时候我们希望合理的协调多个线程之间的执行先后顺序.

完成这个协调工作, 主要涉及到三个方法

wait() / wait(long timeout): 让当前线程进入等待状态.

notify() / notifyAll(): 唤醒在当前对象上等待的线程.

注意: wait, notify, notifyAll 都是 Object 类的方法.

5.1.wait方法的使用

wait()方法要做的事情:

  1. 释放当前的锁(前提是你得有锁,不然怎么释放)
  2. 线程进入阻塞
  3. 线程被唤醒, 重新尝试获取这个锁.

wait 要搭配 synchronized 来使用. 脱离 synchronized 使用 wait 会直接抛出异常.

  public static void main(String[] args) throws InterruptedException {Object locker = new Object();System.out.println("wait 之前");locker.wait();  //没加锁,会抛出异常System.out.println("wait 之后");}

wait 结束等待的条件:

1.其他线程调用该对象的 notify 方法.

2.wait 等待时间超时 (wait 方法提供一个带有 timeout 参数的版本, 来指定等待时间).

3.其他线程调用该等待线程的 interrupted 方法, 导致 wait 抛出 InterruptedException 异常.

接下来我们看一个代码

  public static void main(String[] args) throws InterruptedException {Object locker = new Object();System.out.println("wait 之前");locker.wait();  // 只要一般涉及阻塞的方法都会抛出异常//locker这个对象只要不notify,这个线程就一直处于waiting状态(加了等待时间就不会了)System.out.println("wait 之后");}

运行结果以及jconsole观察到的结果(这个程序就一直等待,死等(除非有等待时间))

5.2.notify方法的使用

我们以代码举例:创建三个线程都去wait,主线程notify唤醒(随机的)

  public static void main(String[] args) throws InterruptedException {Object locker = new Object(); // 公用一个锁对象Thread t1 = new Thread(() ->{synchronized (locker){try {locker.wait();} catch (InterruptedException e) {throw new RuntimeException(e);}}System.out.println("t1 醒了");});Thread t2 = new Thread(()-> {synchronized (locker){try {locker.wait();} catch (InterruptedException e) {throw new RuntimeException(e);}}System.out.println("t2 醒了");});Thread t3 = new Thread(()->{synchronized(locker){try {locker.wait();} catch (InterruptedException e) {throw new RuntimeException(e);}}System.out.println("t2 醒了");});t1.start();t2.start();t3.start();System.out.println("唤醒其中一个线程");Thread.sleep(1000);  // 确保其他线程已经处于waiting状态synchronized(locker){locker.notify();// 也要记得加锁呀,不然咋释放锁}}

结果:可以看到随机一个线程被唤醒,其他线程在waiting状态

如果是notifyAll方法呢?(三个线程都被唤醒了,但是第一个拿到锁的线程如果执行的任务比较多,另外两个线程会处于BLOCKED状态(由于锁竞争导致的阻塞))

6.wait和notify可以避免线程饿死

先介绍synchronized是可重入锁,什么是可重入锁呢?一个线程对一个对象连续加锁两次不会出现死锁。就譬如这个按理说会出现死锁但是我是可重入的所以不会形成死锁

说到死锁:举一个例子()(这样一个线程想要多把锁,进而形成环,直接卡死就会导致死锁)

说到环就想到哲学家问题

总结:四个成因(破坏一个就解除)

 class Singleton {private static Singleton instance = new Singleton();public static Singleton getInstance(){  // 一定要是静态方法,不然一开始别人都拿不到这个对象,又没办法调用这个方法,岂不是贻笑大方return instance;}private Singleton(){} // 啥也不用干,也干了呀,把构造方法给藏起来了
}public class SingletonDemo{public static void main(String[] args) {Singleton singleton = new Singleton();}
}

上述就是wait和notify : 避免线程饿死(以及votile内存可见性和指令重排序问题)的全部内容啦

能看到这里相信您一定对小编的文章有了一定的认可。

有什么问题欢迎各位大佬指出
欢迎各位大佬评论区留言修正~~

您的支持就是我最大的动力​​​!!!

http://www.dtcms.com/wzjs/86112.html

相关文章:

  • 关于网站设计的毕业论文题目郑州网站关键词优化公司哪家好
  • 做微信小程序的网站外包seo服务口碑好
  • 网站内部资源推广怎么做百度天眼查
  • 成都 企业网站建设公司外链论坛
  • 广州印刷网站建设百度热搜榜历史
  • 武汉找人做网站微信软文模板
  • 高端网站建设高端网站建设专家网站推广平台排行
  • 国内简约网站网络热词2021
  • 网站开发的研究现状正规的关键词优化软件
  • 百度推广太原网站建设百度网盘官网登陆入口
  • jsp网站开发难吗培训心得体会范文500字
  • 家纺营销型网站市场营销推广策划
  • 建站之星怎么使用竞价托管哪家效果好
  • 响应式网站建设济南毛戈平化妆培训学校官网
  • 网站上面图片上传尺寸谷歌站长平台
  • 公众号第三方建微网站最近营销热点
  • wordpress importseo的优点有哪些
  • 百万网站建设报价百度免费发布信息
  • 武义县网站制作哪里可以做
  • 网站平台管理优化方案设计现在最火的推广平台
  • 哈尔滨网站制作招聘网站排名优化方案
  • 各大高校的校园网站建设易观数据app排行
  • 网站文章不收录怎么做网站定制
  • 青岛做网站大公司有哪些百度权重1是什么意思
  • 南宁做棋牌网站的公司seo排名点击器原理
  • 会计公司网站样式注册域名费用一般多少钱
  • 做图片网站 服务器个人博客搭建
  • 百度网站管理搜索引擎优化策略
  • 网软志成个人商城网站sem优化服务公司
  • 微信服务号可以做万网站么seo优化常识