线程六个状态:
- public enum State {
- /**
- * 新生
- */
- NEW,
-
- /**
- * 运行
- */
- RUNNABLE,
-
- /**
- *阻塞
- */
- BLOCKED,
-
- /**
- * 等待
- */
- WAITING,
-
- /**
- * 超时等待
- */
- TIMED_WAITING,
-
- /**
- 死亡
- **/
- TERMINATED;
- }
synchronized和lock的区别
1、synchronized是关键字,lock是类
2、synchronized全自动获取释放,lock手动
3、synchronized标识后,线程A执行,线程B会一直等待,lock可以中途释放
4、synchronized适合少量的数代码,lock用于大亮代码加锁。
经典问题,生产者、消费者
public static void main(String[] args) { t2 t2 = new t2(); new Thread(() -> { for (int i = 0; i < 50; i++) { try { t2.add(); } catch (InterruptedException e) { throw new RuntimeException(e); } } }).start(); new Thread(() -> { for (int i = 0; i < 50; i++) { try { t2.delete(); } catch (InterruptedException e) { throw new RuntimeException(e); } } }).start(); } int sum = 0; public synchronized void add() throws InterruptedException { //while(sum==0) if (sum != 0) { this.wait(); } sum++; System.out.println(sum + "生产了一个东西"); this.notify(); } public synchronized void delete() throws InterruptedException { //while(sum==0) if (sum == 0) { this.wait(); } sum--; System.out.println(sum + "使用了一个东西"); this.notify(); }以上代码看着和用着都没问题,问题出在,一旦我多几个线程运行就会出现数据错误:
而且还有几率一直某一个线程处于等待状态,无法被唤醒 :
我的理解是cpu执行的数据很快,假如在某一刻A线程处于等待,B线程也处于等待,此时C线程唤醒了,这两个同时被唤醒,就出现了多次消费,虚假唤醒,其实就只能消费一次。
所以我们不能使用一次if作为判断,应该使用while作为判断,
然后就是使用java多线程包下的Condition ,它也可以阻塞、唤醒线程,它还有一个优势就是可以指定唤醒某一个线程。
- package com.quxiao.controller;
-
- import java.util.concurrent.locks.Condition;
- import java.util.concurrent.locks.Lock;
- import java.util.concurrent.locks.ReentrantLock;
-
- /**
- * @program: package1
- * @author: quxiao
- * @create: 2023-09-27 15:22
- **/
- public class t3 {
- public static void main(String[] args) {
- t3 t3 = new t3();
- new Thread(() -> {
- for (int i = 0; i < 10; i++) {
- t3.a();
- }
- }, "a").start();
- new Thread(() -> {
- for (int i = 0; i < 10; i++) {
- t3.b();
- }
- }, "b").start();
- new Thread(() -> {
- for (int i = 0; i < 10; i++) {
- t3.c();
- }
- }, "c").start();
- }
-
- int sum = 1;
- Lock lock = new ReentrantLock();
- Condition aLock = lock.newCondition();
- Condition bLock = lock.newCondition();
- Condition cLock = lock.newCondition();
-
- void a() {
- lock.lock();
- try {
- while (sum != 1) {
- aLock.await();
- }
- System.out.println(Thread.currentThread().getName()+":" + "AAAA");
- sum = 2;
- bLock.signal();
- } catch (InterruptedException e) {
- throw new RuntimeException(e);
- } finally {
- lock.unlock();
- }
-
- }
-
- void b() {
- lock.lock();
- try {
- while (sum != 2) {
- bLock.await();
- }
- System.out.println(Thread.currentThread().getName()+":" + "BBBB");
- sum = 3;
- cLock.signal();
- } catch (InterruptedException e) {
- throw new RuntimeException(e);
- } finally {
- lock.unlock();
- }
-
- }
-
- void c() {
- lock.lock();
- try {
- while (sum != 3) {
- cLock.await();
- }
- System.out.println(Thread.currentThread().getName()+":" + "CCCC");
- sum = 1;
- aLock.signal();
- } catch (InterruptedException e) {
- throw new RuntimeException(e);
- } finally {
- lock.unlock();
- }
-
- }
- }