一、并发编程所带来的另外一个挑战-死锁
在我们的开发过程中,或多或少遇到过并发的死锁的问题
举个生活中的例子:比如我们小的时候打架,很喜欢抓对方的头发的
①、我自己捂住自己的头发,然后我尝试去抓对方的头发,然而对方也捂住自己的头发,然而它也想抓我的头发,那么这回就处于一种僵局,也有可能我抓不住对方的头发,对方也抓不住我的头发,这时两个人在这里僵持着,这就很像在我们并发编程中的死锁。
②、也就是大家各有手头上的资源,然后去访问对方的资源,可以通过两个对象来代替两个锁
代码演示下:
package com.weizhaoyang;public class DeadThreadDemo {private static final Object HAIR_A=new Object();private static final Object HAIR_B=new Object();public static void main(String[] args) {new Thread(()->{synchronized (HAIR_A){synchronized(HAIR_B){try {Thread.sleep(5000000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println("A成功抓住B的头发");}}}).start();new Thread(()->{synchronized (HAIR_B){synchronized (HAIR_A){System.out.println("B成功抓住A的头发");}}}).start();;}}
运行的结果如下:这就是产生死锁了
二、并发编程所带来的另外一个挑战-线程安全的问题
线程的安全的问题和死锁的区别非常大:
①、死锁的状态好判断,它会处于一种僵持的状态,可以通过jdk提供的相应的工具,可以非常快速的定位到这个问题。
②、线程安全性问题,你去运行的时候,它并没有很明显的特征,比如说运行起来看起来是非常正常的。
代码如下:
package com.weizhaoyang;import java.util.concurrent.CountDownLatch;public class UnSafeDemo {private static int num=0;private static CountDownLatch countDownLatch=new CountDownLatch(10);public static void inCreate(){num++;}public static void main(String[] args) {for(int i=0;i<10;i++){new Thread(()->{for(int j=0;j<100;j++){inCreate();}}).start();countDownLatch.countDown();}while(true){if(countDownLatch.getCount()==0){System.out.println(num);break;}}}}
运行的结果如下:这时的结果始终是小于1000的。
解释如下:可以用两个线程解释下:当线程1还没有执行到num++的时候,线程2就拿到了时间片,这时就把num++,这时就是两个线程的结果为1。所以10个线程各执行100次的时候结果小于1000.
三、并发编程所带来的另外一个挑战-资源的限制
这是一个外在的因素,在资源有限制的情况下,并不是开越多的线程越好
主要分为两个方面:①、硬件资源
服务器:1m
本机: 2m
带宽的大小会影响并发编程
还有硬盘读写的速度
cpu的大小,不会因为开起多个线程,就速度变快,有可能会变慢
②、软件的资源
数据库连接 500个连接, 1000个线程查询,并不会因此而加快
或者socket编程。
var first_sceen__time = (+new Date()); if ("" == 1 && document.getElementById('js_content')) { document.getElementById('js_content').addEventListener("selectstart",function(e){ e.preventDefault(); }); }
阅读 45