Thread 类的基本用法

1.线程的创建

线程有五种创建方法(一般使用lambda表达式):

(1)继承 Thread, 重写 run

class MyThread extends Thread {
    public void run() {
        System.out.println("重写run");
    }
}
public class Demo1 {
    public static void main(String[] args) {
           MyThread t = new MyThread();
           t.start();
    }
}

(2)实现 Runnable, 重写 run

class MyRunnable implements Runnable{
    @Override
    public void run() {
        while(true) {
            System.out.println("实现 Runnable, 重写 run");
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}
public class Demo2 {
    public static void main(String[] args) {
        MyRunnable runnable = new MyRunnable();
        Thread t= new Thread(runnable);
        t.start();

        while(true) {
            System.out.println("你好");
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}

(3)继承 Thread, 重写 run, 使用匿名内部类

public class Demo3 {
    public static void main(String[] args) {
        Thread t = new Thread(){
            public void run() {
                while(true) {
                    System.out.println("你好");
                    try {
                        Thread.sleep(1000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        };
        t.start();
    }
}

(4)实现 Runnable, 重写 run, 使用匿名内部类

public class Demo4 {
    public static void main(String[] args) {
        Thread t = new Thread(new Runnable() {
            @Override
            public void run() {
                while(true) {
                    System.out.println("你好");
                    try {
                        Thread.sleep(1000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        });
        t.start();
    }
}

(5)使用 lambda 表达式

public class Demo5 {
    public static void main(String[] args) {
        Thread t = new Thread(() -> {
            while(true) {
                System.out.println("你好");
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        });
        t.start();
    }
}

2.线程中断

线程中断有两种:
(1)自己定义一个标注位,作为线程是否结束的标记

public class Demo8 {
    private static boolean isSign = false;//标志位

    public static void main(String[] args) {
        Thread t = new Thread(() -> {
           while(!isSign) {
               System.out.println("你好");
               try {
                   Thread.sleep(1000);
               } catch (InterruptedException e) {
                   e.printStackTrace();
               }
           }
            System.out.println("t线程打印完成");
        });

        t.start();
        try {
            Thread.sleep(5000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }

        isSign = true;
        System.out.println("设置t 线程中断");
    }
}

(2)使用标准库自带的标志位

public class Demo9 {
    public static void main(String[] args) {
        Thread t = new Thread(() -> {
            while(!Thread.currentThread().isInterrupted()) {
                System.out.println("你好");
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    //e.printStackTrace();
                    break;
                    //这个地方换成break
                }
            }
            System.out.println("t线程打印完成");
        });
        t.start();
        try {
            Thread.sleep(5000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        t.interrupt();
        System.out.println("设置t 线程中断");
    }
}

interrupt 方法的行为有两种情况
1.t线程在运行状态,会把Thread.currentThread().isInterrupted()这个标注位设置位true
2.t线程在阻塞状态(sleep)就不会设置标志位,而是触发一个InterruptedException,这个异常会把sleep提前唤醒,但e.printStackTrace()只是打印了日志,并没有结束循环,所以会导致继续执行,把catch里换成break就能解决了

3.线程等待

使用join,在main线程中调用t.join就是让main线程阻塞等待,等到t执行完了,main才能继续执行

public class Demo10 {
    public static void main(String[] args) {
        Thread t =new Thread(() -> {
           for (int i = 0; i < 5; i++) {
               System.out.println("你好");
           }
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        });

        t.start();
        System.out.println("main 线程join之前");
        try {
            t.join();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println("main线程join之后");
        System.out.println("不好");
    }

}

执行结果:
在这里插入图片描述

4.线程休眠

sleep会让线程休息一会(阻塞等待)
可以看作有两个队列,像链表那样串在一起,一个是就绪队列,一个是阻塞队列,操作系统在管理这些PCB时会有多个链表.
例如我们使用了Thread.sleep(1000),就能把这个线程由就绪队列放到阻塞队列当中,不是说只阻塞1000ms,而是要至少1000ms,下一次使用的时间是由操作系统的需求来决定的,

5.获取线程实例

使用Thread.currentThread()来获取

public class Demo11 {
    public static void main(String[] args) {
        Thread t = new Thread(() -> {
            Thread thread = Thread.currentThread();
            System.out.println(thread.getName());
        });
        t.start();
        Thread thread = Thread.currentThread();
        System.out.println(thread.getName());
    }
}

代码结果:
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值