Java-进阶:多线程1,2024字节跳动Java面试真题解析

//异常的意义:即使我的线程被异常终止,我也可以保证资源的正常释放
}
}
}

//会抛出 java.lang.InterruptedException: sleep interrupted

4. JAVA程序的运行原理

  • Java命令会启动 JVM,即启动了一个进程,该进程会启动一个主线程,然后主线程调用某个类的 main方法,所以 main方法 都是运行在主线程里
  • jvm 启动后,必然有一个执行路径(线程)从 main方法开始的,一直执行到 main方法结束,这个线程在Java中称之为主线程
  • 当程序的主线程执行时,如果遇到了循环而导致程序在指定位置停留时间过长,则无法马上执行下面的程序,需要等待循环结束后能够执行
  • 方法在哪个线程中被调用,它就运行在哪个线程中
  • JVM 是一个多线程程序,每个Java 进程都分配一个 JVM 实例

public class ThreadDemo {
public static void main(String[] args) {
//利用垃圾回收器来证明
while(true) {
//这里虽然一直在堆空间中,创建数组对象,
// 但是始终没有耗尽堆空间,就是因为垃圾回收器,
// 在另外一个线程中,帮我们回收垃圾,所以才不会耗尽heap内存
// 从而证明,jvm是线程的
int[] ints = new int[1024];
ints = null;
}
}
}


二、Thread 类

1. 概述

  • Thread是程序中的执行线程。Java 虚拟机允许应用程序并发地运行多个执行线程
  • 不是抽象类

2. 构造方法

  • Thread(): 分配新的 Thread 对象
  • Thread(String name):分配新的 Thread 对象,将指定的 name 作为其线程名称

3. 常用方法

  • void start():使该线程开始执行,Java虚拟机调用线程的 run 方法
  • void run():该线程要执行的操作,
  • static void sleep(long millis):在指定毫秒内让当前正在执行的线程休眠,暂停执行
  • static Thread currentThread():返回当前正在执行的线程对象的引用Thread.currentThread()

4. 创建新执行线程的两种方法

  • 将类声明为 Thread 的子类。该子类应重写 Thread 类的 run 方法。创建对象,开启线程。run方法相当于其他线程的main方法。
  • 声明一个实现 Runnable 接口的类。该类然后实现 run 方法。然后创建 Runnable 的子类对象,传入到某个线程的构造方法中,开启线程。

虽然实现线程有两种方式,其实从客观来讲,线程本身只代表独立的执行路径, 执行的具体内容其实是Task本身,和执行路径的实现本身没有联系;只是我们开发者,想将一个task放在某条独立的执行路径(Thread 类对象,也就是一个线程中)来运行


三、创建线程:继承 Thread 类

  • 创建线程的步骤

  • 定义一个类继承 Thread

  • 重写 run方法

  • 创建子类对象,就是创建线程对象

  • 调用 start 方法,开启线程并让线程执行,同时还会告诉jvm去调用 run 方法

线程对象调用 run方法 不开启线程。仅是对象调用方法。 
线程对象调用 start 开启线程,并让 jvm 调用 run 方法在开启的线程中执行

//测试类
public class Test {
public static void main(String[] args) {
//创建自定义线程对象
MyThread mt = new MyThread(“新的线程!”);

//错误启动线程,这只是普通的方法调用
//firstThread.run();

//开启新线程
mt.start();

//再次启动一个线程,会抛异常IllegalThreadStateException
//因为一个线程对象只能启动一次,
// 如果同一个线程对象,启动多次,就会抛出异常
//firstThread.start();
//只能创建一个新的对象
new MyThread(“第二个线程!”).start();
//获取主线程的名字
System.out.println(Thread.currentThread().getName()+“:主线程!”);
}
}

//自定义线程
class MyThread extends Thread {
//定义指定线程名称的构造方法
public MyThread(String name) {
//调用父类的String参数的构造方法,指定线程的名称
super(name);
}

//重写run方法,完成该线程执行的逻辑
@Override
public void run() {
//获取线程的名字getName()
System.out.println(getName() + “:正在执行!”);
}
}


四、创建线程:实现 Runnable 接口

1. Runnable 接口的构造方法

  • Thread(Runnable target): 分配新的 Thread 对象,以便将 target 作为其运行对象
  • Thread(Runnable target,String name) : 分配新的 Thread 对象,以便将 target 作为其运行对象;并将指定的 name 作为其名称

2. 创建线程的步骤

  • 定义类实现 Runnable 接口。
  • 覆盖接口中的 run方法
  • 创建 Thread类的 对象
  • 将 Runnable接口 的子类对象作为参数传递给 Thread 类 的构造方法
  • 调用 Thread类的 start() 开启线程。

Thread 类的构造函数:
1. Thread(): 分配新的 Thread 对象
2. Thread(String name):分配新的 Thread 对象,将指定的 name 作为其线程名称

//测试类
public class Test {
public static void main(String[] args) {
//创建实现 Runnable 接口的子类对象
MyRunnable myrunnable = new MyRunnable();
//创建Thread实例,在Thread的构造方法中传递Runnable实例
//Runnable就代表在 Thread 上运行的任务
Thread thread = new Thread(myrunnable);
//开启线程
thread.start();
for (int i = 0; i < 10; i++) {
System.out.println(“main线程:正在执行!”+i);
}
}
}

//自定义线程执行任务类
class MyRunnable implements Runnable{
//定义线程要执行的run方法逻辑
//run方法,不能抛出编译时异常
//run方法,没有参数没有返回值
@Override
public void run() {
for (int i = 0; i < 5; i++) {
System.out.println(“我的线程:正在执行!”+i);
}
}
}

3. 实现 Runnable 接口的原理

为什么需要定一个类去实现Runnable接口呢?继承Thread类和实现Runnable接口有啥区别呢? 
只有创建Thread类的对象才可以创建线程。线程任务已被封装到Runnable接口的run方法中,而这个run方法所属于Runnable接口的子类对象,所以将这个子类对象作为参数传递给Thread的构造函数,这样,线程对象创建时就可以明确要运行的线程的任务

4. 两种方式的比较

  • 继承 Thread 类方式

  • 如果某个类已经有父类,则无法再继承 Thread 类

  • 实现 Runnable 接口方式

  • 解决了方式一的单继承的局限性

  • 还有一个优点,便于多线程共享数据

第二种方式实现Runnable接口避免了单继承的局限性,所以较为常用。实现Runnable接口的方式,更加的符合面向对象;线程分为两部分,一部分线程对象,一部分线程任务。

  • 继承Thread类,线程对象和线程任务耦合在一起。一旦创建Thread类的子类对象,既是线程对象,有又有线程任务
  • 实现runnable接口,将线程任务单独分离出来封装成对象类型就是Runnable接口类型。Runnable接口对线程对象和线程任务进行解耦

五、线程优先级

1. 概述

  • 我们可以通过 Thread 类中:

  • getPriority 方法 :获取 线程的优先级

  • setPriority 方法 :设置 线程的优先级

2. 线程优先级的范围

  • 如果设置线程优先级的范围,超出了规定范围,会抛出异常;

MAX_PRIORITY 10 //最大优先级 
MIN_PRIORITY 1 //最小优先级 
NORM_PRIORITY 5 //默认优先级

//使用
thread1.setPriority(Thread.MAX_PRIORITY); //设置
thread2.setPriority(Thread.MIN_PRIORITY);
System.out.println(thread1.getPriority());//获取

小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。

深知大多数初中级Java工程师,想要提升技能,往往是自己摸索成长,但自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年最新Java开发全套学习资料》送给大家,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
img
img
img

由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频

如果你觉得这些内容对你有帮助,可以添加下面V无偿领取!(备注Java)
img

总结

总体来说,如果你想转行从事程序员的工作,Java开发一定可以作为你的第一选择。但是不管你选择什么编程语言,提升自己的硬件实力才是拿高薪的唯一手段。

如果你以这份学习路线来学习,你会有一个比较系统化的知识网络,也不至于把知识学习得很零散。我个人是完全不建议刚开始就看《Java编程思想》、《Java核心技术》这些书籍,看完你肯定会放弃学习。建议可以看一些视频来学习,当自己能上手再买这些书看又是非常有收获的事了。

员的工作,Java开发一定可以作为你的第一选择。但是不管你选择什么编程语言,提升自己的硬件实力才是拿高薪的唯一手段。

如果你以这份学习路线来学习,你会有一个比较系统化的知识网络,也不至于把知识学习得很零散。我个人是完全不建议刚开始就看《Java编程思想》、《Java核心技术》这些书籍,看完你肯定会放弃学习。建议可以看一些视频来学习,当自己能上手再买这些书看又是非常有收获的事了。

[外链图片转存中…(img-hvWm6pMH-1711137660767)]

本文已被CODING开源项目:【一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码】收录

  • 19
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值