java多线程的学习之路(一)

笔记来源

java多线程的学习之路(二)

一、线程的生命周期

生命周期:

在程序开发中,将一个对象从被实例化完成,到这个对象使用结束,并销毁,将这样的过程称为对象的生命周期。类似于人的一生。

线程的生命周期: .

一个线程被实例化完成,到这个线程销毁,中间的过程。

线程的状态:

  1. 新生态: New
    一个线程对象被实例化完成,但是还没有做任何的操作。
  2. 就绪态: Ready
    一个线程已经被开启,已经开始争抢CPU时间片。
  3. 运行态: Run
    一个线程抢到了CPU时间片,开始执行这个线程中的逻辑。
  4. 阻塞态: Interrupt
    一个线程在运行的过程中,受到某些操作的影响,放弃了已经获取到的CPU时间片,并且不再参与CPU时间片的争
    抢,此时线程处于挂起状态。
  5. 死亡态: Dead
    一个线程对象需要被销毁。

线程状态之间的转换关系:
在这里插入图片描述


二、线程的实例化

第一种方式:继承Thread类

public class ThreadCreate {
    public static void main(String[] args) {
        //线程实例化
        /* 1.继承Thread类, 做一个线程子类(自定义的线程类)*/
        MyThread mt = new MyThread();

        //注意:
        //需要调用start方法,使线程启动。
        // start方法会开启一个新的线程,来执行run中的逻辑
        //如果直接调用run方法,则线程mt不会进入就绪态
        mt.start();

        System.out.println("主线程逻辑结束了");
    }
}

//自定义的线程子类
class MyThread extends Thread{
    /*
     * 重写run方法
     * 将需要并发执行的任务写到run方法中
     */
    @Override
    public void run() {
        for(int i = 1;i <= 5;i++)
            System.out.println("子线程中的逻辑:"+ i);
    }
}

输出结果:

主线程逻辑结束了
子线程中的逻辑:1
子线程中的逻辑:2
子线程中的逻辑:3
子线程中的逻辑:4
子线程中的逻辑:5

第二种方式:实现Runnable接口

public class ThreadCreate {
    public static void main(String[] args) {
        //匿名方法
        Runnable r = new Runnable() {
            @Override
            public void run() {
                for (int i = 1; i<=5; i++)
                    System.out.println("子线程1中的逻辑:"+ i);
            }
        };

        //lambda表达式
        Runnable r1 = ()->{
            for (int i = 1; i<=5; i++)
                System.out.println("子线程2中的逻辑:"+ i);
        };

        Thread t = new Thread(r); t.start();
        Thread t1 = new Thread(r1); t1.start();

        System.out.println("主线程逻辑结束了");
    }
}

输出结果:

主线程逻辑结束了
子线程2中的逻辑:1
子线程2中的逻辑:2
子线程2中的逻辑:3
子线程2中的逻辑:4
子线程1中的逻辑:1
子线程2中的逻辑:5
子线程1中的逻辑:2
子线程1中的逻辑:3
子线程1中的逻辑:4
子线程1中的逻辑:5

因为Java是单继承的,更多使用实现Runnable接口的方法。


三、线程的命名

public class ThreadMethod {
    public static void main(String[] args) {
        //线程的命名

        //1.set方法
        Thread t = new Thread();
        t.setName("custom");
        System.out.println(t.getName());

        //2.构造方法
        //new Thread(Runnable r, String name)
        Thread t1 = new Thread(()->{},"custom2");
        System.out.println(t1.getName());
    }
}

四、线程的休眠

public class ThreadMethod {
    public static void main(String[] args) {
        MyThread2 myThread2 = new MyThread2();
        myThread2.start();
    }
}

//自定义的线程子类
class MyThread2 extends Thread{
    /*
     * 重写run方法
     * 将需要并发执行的任务写到run方法中
     */
    @Override
    public void run() {
        for (int i = 0; i < 5; i++) {
            System.out.println(i);
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}

输出:每隔一秒输出一个数字。


五、线程的优先级

设置线程的优先级,只是修改这个线程可以去抢到CPU时间片的概率

public class ThreadMethod {
    public static void main(String[] args) {
        threadPriority();
    }

    /*
   	 * 设置线程的优先级
   	 */
    private static void threadPriority() {
        //设置线程的优先级,只是修改这个线程可以去抢到CPU时间片的概率。
        //并不是优先级高的线程一定能抢到CPU时间片
        //优先级的设置,是一个整数,[0, 10]的整数,默认是5
        Runnable r1 = ()->{
            for (int i = 0; i < 5; i++) {
                System.out.println(Thread.currentThread().getName()+" "+i);
            }
        };

        Thread t1 = new Thread(r1);
        Thread t2 = new Thread(r1);
        
		//设置优先级必须放到start之前
        t1.setPriority(7);

        t1.start();
        t2.start();
    }
}

如果不设置优先级,两个线程的默认优先级为5:

Thread-0 0
Thread-1 0
Thread-0 1
Thread-1 1
Thread-0 2
Thread-1 2
Thread-0 3
Thread-1 3
Thread-0 4
Thread-1 4

设置了线程0的优先级为7以后,线程0强夺到CPU的概率更大:

Thread-0 0
Thread-1 0
Thread-0 1
Thread-0 2
Thread-0 3
Thread-0 4
Thread-1 1
Thread-1 2
Thread-1 3
Thread-1 4


六、线程的礼让

public class ThreadMethod {
    public static void main(String[] args) {
        threadYield();
    }

    /*线程的礼让..*/
    private static void threadYield(){
        //当前线程从 run->ready,释放CPU资源
        Runnable r1 = ()->{
            for (int i = 0; i < 10; i++) {
                System.out.println(Thread.currentThread().getName()+" "+i);
                if(i==3)
                    Thread.yield();
            }
        };
        Thread t1 = new Thread(r1,"Thread-1");
        Thread t2 = new Thread(r1,"Thread-2");
        t1.start();
        t2.start();
    }
}

当线程1的i = 3时,线程1礼让,线程0强夺到CPU

Thread-1 0
Thread-1 1
Thread-1 2
Thread-1 3
Thread-2 0
Thread-1 4
Thread-2 1
Thread-1 5
Thread-2 2
Thread-1 6
Thread-2 3
Thread-1 7
Thread-2 4
Thread-2 5
Thread-2 6
Thread-1 8
Thread-2 7
Thread-1 9
Thread-2 8
Thread-2 9

原文地址:https://www.cnblogs.com/csyxsy/p/13340210.html