多线程学习笔记

线程核心介绍:

在这里插入图片描述

1.实现线程的方法

1.通过继承thread来实现

public class ThreadTest extends Thread{
    public void run(){
        for (int i = 0; i <1000 ; i++) {
            System.out.println("run方法"+i);
        }
    }

    public static void main(String[] args) {
        ThreadTest t1=new ThreadTest();
        t1.start();

        for (int i = 0; i <1000 ; i++) {
            System.out.println("main方法"+i);
        }

    }
}

注意:线程开启不一定立即执行,由cpu调度完成。

2.通过runnable接口来实现

package com.company;

public class ThreadTest01 implements Runnable {
    @Override
    public void run() {
        for (int i = 0; i <2000 ; i++) {
            System.out.println("run"+i);
        }
    }

    public static void main(String[] args) {

        ThreadTest01 t1=new ThreadTest01();
        new Thread(t1).start();
        for (int i = 0; i <1000 ; i++) {
            System.out.println("main"+i);
        }
    }
}

3.二者对比

在这里插入图片描述

2.初识并发性

1.抢票范例

package com.company;

public class ThreadTest02 implements Runnable {
    private int ticketCount=10;
    @Override
    public void run() {
        while (true){
            if(ticketCount<=0){
                break;
            }
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println(Thread.currentThread().getName()+"抢到了第"+ticketCount--+"张票");
        }
    }

    public static void main(String[] args) {
        ThreadTest02 threadTest02=new ThreadTest02();
        new Thread(threadTest02,"小明").start();
        new Thread(threadTest02,"黄牛").start();
    }
}

2.龟兔赛跑

package com.company;

public class Race implements Runnable {
    public static String winner;
    public void run() {
        for (int i = 0; i <=101 ; i++) {
            boolean flag=GameOver(i);
            if(flag){
                break;
            }
            System.out.println(Thread.currentThread().getName()+"跑了"+ i +"步");
        }

    }

    public boolean GameOver(int step){
        if(winner!=null){
            return true;
        }else if(step>100){
            winner=Thread.currentThread().getName();
            System.out.println("winner is"+winner);
            return true;
        }
        return false;
    }

    public static void main(String[] args) {
        Race race=new Race();
        new Thread(race,"乌龟").start();
        new Thread(race,"兔子").start();
    }

}

3.静态代理模式

package com.company;
//静态代理模式总结:
//代理角色和真实角色要实现同一个接口
//代理角色代理真实角色

public interface StaticProxy {
    void marry();
}
class WeedingPerson implements  StaticProxy{

    @Override
    public void marry() {
        System.out.println("结婚了很开心");
    }
}
class MarryCompany implements StaticProxy{
public static WeedingPerson weedingPerson;

    public MarryCompany(WeedingPerson weedingPerson){
        this.weedingPerson=weedingPerson;
    }

    @Override
    public void marry() {
        before();
        this.weedingPerson.marry();
        after();
    }

    private void after() {
        System.out.println("数钱");
    }

    private void before() {
        System.out.println("布置现场");
    }
}

class Test{
    public static void main(String[] args) {
        WeedingPerson weedingPerson=new WeedingPerson();
        MarryCompany marryCompany=new MarryCompany(weedingPerson);
        marryCompany.marry();
    }
}

4.lamda表达式

1.函数式接口

在这里插入图片描述

2.代码实现

package com.baidu.www;

public class TestLamda {
    //静态内部方法
    static class Lamdad1 implements Lamda {

        @Override
        public void f() {
            System.out.println("输出f1方法");
        }

        public static void main(String[] args) {

            Lamda lamda = new Lamdad();
            lamda.f();
            lamda = new Lamdad1();
            lamda.f();
      //局部内部方法
            class Lamdad2 implements Lamda {

                @Override
                public void f() {
                    System.out.println("输出f2方法");
                }
            }

            lamda = new Lamdad2();
            lamda.f();

            //匿名内部类

            lamda=new Lamdad() {
                @Override
                public void f() {
                    System.out.println("输出f3方法");
                }
            };

            lamda.f();

            //lamda表达式
            lamda= ()->{
                System.out.println("输出f4");
            };
            lamda.f();
        }
    }
}

    //定义一个函数式接口
    interface Lamda {
        void f();
    }
//接口实现类
    class Lamdad implements Lamda {

        @Override
        public void f() {
            System.out.println("输出f方法");
        }
    }

5.线程的五大状态

1.线程生命周期

在这里插入图片描述

2.线程方法

在这里插入图片描述

3.线程停止代码操作

package com.baidu.www;

public class ThreadTest03 implements Runnable{
    //外部标志位
    boolean flag=true;
    @Override
    public void run() {
        int i=0;
        while(flag){

                System.out.println("线程运行"+i++);
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }


        }
    }

    public void stop(){
        this.flag=false;
    }

    public static void main(String[] args) throws InterruptedException {
        ThreadTest03 threadtest03=new ThreadTest03();
        new Thread(threadtest03).start();
        for (int i = 0; i <10 ; i++) {
            Thread.sleep(1000);
            System.out.println("主线程"+i);
            if(i==4){
                threadtest03.stop();
                System.out.println("线程停止");
            }
        }
    }
}

4.线程休眠

在这里插入图片描述

5.礼让方法

在这里插入图片描述

6.join方法

简单,一笔带过,类似于插队。

6.线程状态

1.代码演示

package com.baidu.www;

public class ThreadTest04 {

    public static void main(String[] args) {
        Thread thread=new Thread(()->{
            for (int i = 0; i <5 ; i++) {
                try {
                    Thread.sleep(1000);
                    System.out.println("线程开启"+i);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
            System.out.println("/");

        });


        Thread.State state=thread.getState();
        System.out.println(state);//线程创建
        thread.start();
        state=thread.getState();
        System.out.println(state);//线程启动

    }

}

2.线程的优先级

在这里插入图片描述

1.代码演示

package com.baidu.www;



public class PriorityTest implements Runnable  {
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName()+"线程的优先级"+Thread.currentThread().getPriority());
    }
    public static void main(String[] args) {
        PriorityTest priorityTest=new PriorityTest();

        Thread t2=new Thread(priorityTest,"t2");
        Thread t3=new Thread(priorityTest,"t3");
        t2.setPriority(Thread.MIN_PRIORITY);
        t3.setPriority(Thread.MAX_PRIORITY);
        t2.start();
        t3.start();
    }


}

3.守护线程

在这里插入图片描述

注释:一句话,用户线程结束,守护线程也结束;

注释:将setDeamon(true);//即为守护线程

7.并发

1.线程同步

在这里插入图片描述

在这里插入图片描述

注释:并发:多个线程同时操作一个对象

synchronized

2.线程不安全实例代码演示

1.抢票实例(已加入synchronized变成同步方法)

package com.baidu.www;

public class UnsafeBuyTicket implements Runnable {

private int ticketNmuber=10;
private boolean flage=true;
    @Override
    public void run() {
        while(flage){
            try {
                Thread.sleep(10);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            buy();
        }

    }
    //买票
    public synchronized void buy(){//加入synchronized关键字变成同步方法
        if(ticketNmuber<=0){
            flage =false;
            return;
        }else if(ticketNmuber<=10){
            flage=true;
            System.out.println(Thread.currentThread().getName()+"拿到了第"+ticketNmuber--+"张票");
            return;

        }
    }

    public static void main(String[] args) {
UnsafeBuyTicket unsafe=new UnsafeBuyTicket();
new Thread(unsafe,"小明").start();
new Thread(unsafe,"黄牛").start();
    }
}

2.银行取钱实例(已加入synchronized变成同步块)

package com.baidu.www;

public class UnsafeBank  {
    public static void main(String[] args) throws InterruptedException {
        BankCount bankCount=new BankCount("结婚基金",100);
        System.out.println("账户里有"+bankCount.bankmoney);
        DrawingMoney yb=new DrawingMoney(bankCount,50,"易彪");
        DrawingMoney yx=new DrawingMoney(bankCount,100,"杨欣");
        new Thread(yb).start();
        new Thread(yx).start();


    }

}
class BankCount{
    String username;
    int bankmoney;//银行账户有多少钱

    public BankCount(String username, int bankmoney) {
        this.username = username;
        this.bankmoney = bankmoney;
    }
}
class DrawingMoney implements Runnable{
  static   BankCount bankCount;
    int nowMoney;//现在手里有多少钱
    int drawingMoney;//要取多少钱
    String name;

    public DrawingMoney(BankCount bankCount, int drawingMoney, String name) {
        this.name=name;
        this.bankCount = bankCount;
        this.drawingMoney=drawingMoney;
    }
    public void run() {
        synchronized(bankCount){
            if(bankCount.bankmoney<drawingMoney) {
                System.out.println("钱不够,取不出来");
                return;
            }else {

                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {


                }
                //银行卡账户余额
                bankCount.bankmoney = bankCount.bankmoney - drawingMoney;
                //你手里的钱
                nowMoney = nowMoney + drawingMoney;
                System.out.println(this.name + "的手里有" + nowMoney);
                System.out.println(bankCount.username + "的余额为" + bankCount.bankmoney);
            }
        }

    }
}

3.ArrayList不安全实例(已加入synchronized变成同步块)

package com.baidu.www;

import java.util.ArrayList;
import java.util.List;

public class ArrayListTest implements Runnable{
    public static void main(String[] args) throws InterruptedException {
        List<String> list=new ArrayList<>();

            synchronized (list) {//加入synchronized关键字变成同步块
                    for (int i = 0; i < 10; i++) {
                    Runnable thread;
                    thread = () -> {
                        list.add(Thread.currentThread().getName());

                    };
                    new Thread(thread).start();

                }
            }
        Thread.sleep(1000);
        System.out.println(list.size());
        }



    @Override
    public void  run() {

    }
}

8.同步方法和同步方法块

1.同步方法概念

在这里插入图片描述

2.同步方法块概念

在这里插入图片描述

9.死锁

1.什么是死锁

在这里插入图片描述

2.死锁的必要条件

在这里插入图片描述

3.死锁的代码演示


package com.baidu.www;

public class DeadLock {
    public static void main(String[] args) {
        Person yx = new Person(0, "杨欣");
        Person yb = new Person(1, "阿彪");
        //Person yt= new Person(1, "阿");
        new Thread(yx).start();
        new Thread(yb).start();
        //new Thread(yt).start();

    }
}

class lipstick {

}

class mirror {

}

class Person implements Runnable {
    //保证需要的资源只有一份
    static lipstick lipstick = new lipstick();
    static mirror mirror = new mirror();
    int choice;
    String name;

    public Person(int choice, String name) {
        this.choice = choice;
        this.name = name;
    }


    public void makeup() throws InterruptedException {

        if (choice == 0) {
            synchronized (lipstick) {
                System.out.println(this.name + "获得了口红的锁");
                Thread.sleep(1000);
            }
            synchronized (mirror) {
                System.out.println(this.name + "获得了镜子的锁");

            }

        } else {
            synchronized (mirror) {
                System.out.println(this.name + "获得了镜子的锁");
                Thread.sleep(1000);
            }
            synchronized (lipstick) {
                System.out.println(this.name + "获得了口红的锁");

            }

        }


    }

    @Override
    public void run() {
        try {
            makeup();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

10.生产者和消费者

1.线程通信

在这里插入图片描述

2.分析

在这里插入图片描述

3.线程通信方法概述

在这里插入图片描述

4.解决方案

在这里插入图片描述

1.管道通信代码实现

还未理解

2.信号量代码实现

3.线程池

©️2020 CSDN 皮肤主题: 数字20 设计师:CSDN官方博客 返回首页