java 网络编程connection timed out是什么意思_Java-JUC并发编程(1)

JUC并发编程

1、什么是JUC

JUC:就是我们Java原生的并发包,和一些常用的工具类!

学完之后,很多知识,但是不知道怎么去用!每学习一个知识点,学完之后,可以替换工作中用到的代码!

680806b2a5ee926f8c4b45f2ade0c356.png

2、线程基础知识回顾

什么是进程和线程?

进程:QQ.exe

线程:打字、自动保存.....

一个进程可以包含多个线程,一个进程至少有一个线程! Java程序至少有两个线程: GC、Main

并发、并行

并发:多个线程操作同一个资源,交替执行的过程!

并行:多个线程同时执行!只有在多核CPU下才能完成!

关于最高效率:所有CPU同时执行!

所以我们使用多线程或者并发编程的目的:提高效率,让CPU一直工作,达到最高处理性能!

线程有几种状态

线程有 6 种状态!

 public enum State {     // java能够创建线程吗? 不能!     // 新建     NEW,     // 运行     RUNNABLE,     // 阻塞     BLOCKED,     // 等待     WAITING,     // 延时等待     TIMED_WAITING,     // 终止!     TERMINATED; }

wait/Sleep区别

1、类不同!

 wait : Obejct 类     Sleep Thread 在juc编程中,线程休眠怎么实现!Thread.Sleep      // 时间单位      TimeUnit.SECONDS.sleep(3);

2、会不会释放资源!

sleep:抱着锁睡得,不会释放锁!wait 会释放锁!

3、使用的范围是不同的;

wait 和 notify 是一组,一般在线程通信的时候使用!

sleep 就是一个单独的方法,在那里都可以用!

4、关于异常;

sleep 需要捕获异常!

3、Lock锁

synchronized 传统的方式!

笔记:

代码:

 import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /*  * JUC之后的操作  * Lock锁 + lambda表达式!  */ public class Demo02 {     public static void main(String[] args) {         // 1、新建资源类         Ticket2 ticket = new Ticket2();         // 2、线程操作资源类 , 所有的函数式接口都可以用 lambda表达式简化!         // lambda表达式 (参数)->{具体的代码}         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"A").start();         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"B").start();         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"C").start();     } } // 依旧是一个资源类 class Ticket2{     // 使用Lock,它是一个对象     // ReentrantLock 可重入锁:回家:大门 (卧室门,厕所门...)     // ReentrantLock 默认是非公平锁!     // 非公平锁: 不公平 (插队,后面的线程可以插队)     // 公平锁: 公平(只能排队,后面的线程无法插队)     private Lock lock = new ReentrantLock();     private int number = 30;     public void saleTicket(){         lock.lock(); // 加锁         try {             // 业务代码             if (number>0){                 System.out.println(Thread.currentThread().getName() + "卖出第"+(number--)+"票,还剩:"+number);             }         } catch (Exception e) {             e.printStackTrace();         } finally {             lock.unlock(); // 解锁         }     } }

问题:

Lock 锁

代码:

 import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /*  * JUC之后的操作  * Lock锁 + lambda表达式!  */ public class Demo02 {     public static void main(String[] args) {         // 1、新建资源类         Ticket2 ticket = new Ticket2();         // 2、线程操作资源类 , 所有的函数式接口都可以用 lambda表达式简化!         // lambda表达式 (参数)->{具体的代码}         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"A").start();         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"B").start();         new Thread(()->{for (int i = 1; i <= 40 ; i++) ticket.saleTicket();},"C").start();     } } // 依旧是一个资源类 class Ticket2{     // 使用Lock,它是一个对象     // ReentrantLock 可重入锁:回家:大门 (卧室门,厕所门...)     // ReentrantLock 默认是非公平锁!     // 非公平锁: 不公平 (插队,后面的线程可以插队)     // 公平锁: 公平(只能排队,后面的线程无法插队)     private Lock lock = new ReentrantLock();     private int number = 30;     public void saleTicket(){         lock.lock(); // 加锁         try {             // 业务代码             if (number>0){                 System.out.println(Thread.currentThread().getName() + "卖出第"+(number--)+"票,还剩:"+number);             }         } catch (Exception e) {             e.printStackTrace();         } finally {             lock.unlock(); // 解锁         }     } }

Synchronized 和 Lock 区别

1、Synchronized 是一个关键字、Lock 是一个对象

2、Synchronized 无法尝试获取锁,Lock 可以尝试获取锁,判断;

3、Synchronized 会自动释放锁(a线程执行完毕,b如果异常了,也会释放锁),lock锁是手动释放锁!如果你不释放就会死锁。

4、Synchronized (线程A(获得锁,如果阻塞),线程B(等待,一直等待);)lock,可以尝试获取锁,失败了之后就放弃

1695e3b7ddff8b607d1b5a3cfaee04ae.png

5、Synchronized 一定是非公平的,但是 Lock 锁可以是公平的,通过参数设置;

6、代码量特别大的时候,我们一般使用Lock实现精准控制,Synchronized 适合代码量比较小的同步问题;

4、生产者消费者问题

面试手写题:单例模式、排序算法、死锁、生产者消费者

线程和线程之间本来是不能通信的,但是有时候我们需要线程之间可以协调操作:

Synchronized 普通版

 // Synchronized 版 /* 目的:有两个线程:A  B ,还有一个值初始为0,        实现两个线程交替执行,对该变量 + 1,-1;交替10次 */ public class Demo03 {     public static void main(String[] args) {         Data data = new Data();         // +1         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.increment();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"A").start();         // -1         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.decrement();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"B").start();     } } // 资源类 // 线程之间的通信: 判断  执行  通知 class Data{      private int number = 0;     // +1     public synchronized void increment() throws InterruptedException {         if (number!=0){ // 判断是否需要等待             this.wait();         }         number++; // 执行         System.out.println(Thread.currentThread().getName()+""+number);         // 通知         this.notifyAll(); //唤醒所有线程     }     // -1     public synchronized void decrement() throws InterruptedException {         if (number==0){ // 判断是否需要等待             this.wait();         }         number--; // 执行         System.out.println(Thread.currentThread().getName()+""+number);         // 通知         this.notifyAll(); //唤醒所有线程     } }

四条线程可以实现交替吗?不能,会产生虚假唤醒问题!

b7be3f545f21d26687d76a0308587640.png

注意if 和 while的区别:

 // Synchronized 版 /* 目的: 有两个线程:A  B ,还有一个值初始为0,        实现两个线程交替执行,对该变量 + 1,-1;交替10次         传统的 wait 和 notify方法不能实现精准唤醒通知!  */ public class Demo03 {     public static void main(String[] args) {         Data data = new Data();         // +1         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.increment();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"A").start();         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.increment();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"C").start();  // -1         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.decrement();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"B").start();         new Thread(()->{             for (int i = 1; i <=10 ; i++) {                 try {                     data.decrement();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"D").start();     } } ​ // 资源类 // 线程之间的通信: 判断  执行  通知 class Data{      private int number = 0;     // +1     public synchronized void increment() throws InterruptedException {         while (number!=0){ // 判断是否需要等待             this.wait();         }         number++; // 执行         System.out.println(Thread.currentThread().getName()+""+number);         // 通知         this.notifyAll(); //唤醒所有线程     }     // -1     public synchronized void decrement() throws InterruptedException {         while (number==0){ // 判断是否需要等待             this.wait();         }         number--; // 执行         System.out.println(Thread.currentThread().getName()+""+number);         // 通知         this.notifyAll(); //唤醒所有线程     } }

新版的写法 JUC 挂钩!

1e35d06bdcd6c1008d3fdc1bbb01d103.png
d4f6c61976c3a5f44824c6ef79734bde.png
 import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /* 实现线程交替执行! 主要的实现目标:精准的唤醒线程!     三个线程:A B C     三个方法:A p5  B p10   C p15 依次循环  */ public class Demo04 {     public static void main(String[] args) {         Data2 data = new Data2();         new Thread(()->{             for (int i = 1; i <= 10; i++) {                 try {                     data.print5();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"A").start();         new Thread(()->{             for (int i = 1; i <= 10; i++) {                 try {                     data.print10();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"B").start();         new Thread(()->{             for (int i = 1; i <= 10; i++) {                 try {                     data.print15();                 } catch (InterruptedException e) {                     e.printStackTrace();                 }             }         },"C").start();     } } // 资源类 class Data2{     private int number = 1; // 1A 2B  3C     private Lock lock = new ReentrantLock();     // 实现精准访问     private Condition condition1 = lock.newCondition();     private Condition condition2 = lock.newCondition();     private Condition condition3 = lock.newCondition(); ​     public void print5() throws InterruptedException { ​         lock.lock(); ​         try {             // 判断             while (number!=1){                 condition1.await();             }             // 执行             for (int i = 1; i <= 5; i++) {                 System.out.println(Thread.currentThread().getName() + "" + i);             }             // 通知第二个线程干活!             number = 2;             condition2.signal(); // 唤醒         } catch (InterruptedException e) {             e.printStackTrace();         } finally {             lock.unlock(); // 一定要解锁         }     }     public void print10() throws InterruptedException {         lock.lock();         try {             // 判断             while (number!=2){                 condition2.await();             }             // 执行             for (int i = 1; i <= 10; i++) {                 System.out.println(Thread.currentThread().getName() + "" + i);             }             // 通知3干活             number = 3;             condition3.signal();         } catch (InterruptedException e) {             e.printStackTrace();         } finally {             lock.unlock();         } ​     } ​     public void print15() throws InterruptedException {         lock.lock();         try {             // 判断             while (number!=3){                 condition3.await();             }             // 执行             for (int i = 1; i <= 15; i++) {                 System.out.println(Thread.currentThread().getName() + "" + i);             }             // 通知 1 干活             number = 1;             condition1.signal();         } catch (InterruptedException e) {             e.printStackTrace();         } finally {             lock.unlock();         }     } ​ }

新的技术出来,一定是可以替换一些旧技术的!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值