当前位置: 首页 > article >正文

【Java多线程编程】创建线程的基本方式

大家好,我是一只爱打拳的程序猿。今天给大家带来的内容是 Java 创建线程的基本方式。

多线程的基本创建方式:

  • 继承Thread类
  • 实现Runnable接口
  • 匿名内部类
  • 使用lambda表达式

目录

1.  继承Thread类

1.1 Thread类启动线程

2. 实现Runnable接口

2.1 创建Thread类实例

3. 变种创建方式

3.1 匿名内部类

3.2 lambda表达式


1.  继承Thread类

在 Java 中可以继承 Thread类 来进行多线程编程,Thread类 是 Java 提供的一个标准库。继承 Thread 类后我们必需重写 Thread 类中的 run方法 来创建该线程。

如自定义 myThread类 继承 Thread类:

class myThread extends Thread {
    @Override
    public void run() {
        System.out.println("这是一个线程!");
    }
}

通过上述代码,就能创建一个线程。我所创建的线程只是一段简单的话"这是一个线程"


1.1 Thread类启动线程

在 main方法 中创建 myThread类 的实例 thread 引用后,我们可以通过 thread 引用来调用 start()方法 来启动刚刚创建好的线程。

class myThread extends Thread {
    @Override
    public void run() {
        System.out.println("这是一个线程!");
    }
}
public class ThreadDemo {
    public static void main(String[] args) {
        myThread thread = new myThread();
        thread.start();//调用start方法
    }
}

运行后输出:

通过上述代码,我们可以了解到。启动线程的方式的调用 start() 方法 ,因此我们把调用 start() 方法叫为线程的启动,而 run() 方法叫为线程的入口

注意,在 main 也是一个线程,因此在 main 方法中 thread引用 启动的线程作为子线程,main 方法作为主线程。

  • 重写 run() 方法并在 run() 方法覆写相关内容就是创建一个“非启动状态”线程
  • 未调用 start() 方法,线程并未在操作系统底层创建线程

我们也可以通过循环的方式来观察线程运行的过程:

class myThread extends Thread {
    @Override
    public void run() {
        int i = 1;
        while (true) {
            System.out.println("这是myThread内的第"+i+"一个线程!");
            i++;
            if (i == 7){
                break;
            }
        }
    }
}
public class ThreadDemo {
        public static void main(String[] args) {
            myThread thread = new myThread(); //实例化myThread对象
            thread.start();//调用start方法
        }

运行后输出

我们也可以通过 Thread类 里面的一个 静态方法 sleep() 来停顿每个线程,sleep 内的参数为毫秒。你想停顿1秒就设参数为1000,以此类推。

注意,调用该方式时我们必须 Alt+Enter 这个方法,来 try/catch 这个异常。这样程序才能正常的运行, try/catch 后的代码为:

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

不必在意 catch 内的内容,我们只需要关注 sleep 内的参数是多少即可。


总结

  • 继承Thread类,必须重写run方法来创建线程
  • 使用start方法来启动线程
  • 使用Thread类中的静态方法sleep可停顿代码
  • 由于sleep是静态方法,我们必须使用try/catch来处理sleep异常

2. 实现Runnable接口

我们可以通过使用 Runnable接口 来创建一个线程。在使用 Runnable接口 后我们也要重写 run方法 并在run方法里面创建一个线程。

class myThread implements Runnable {
    @Override
    public void run() {
        System.out.println("Hello World");
    }
}

通过上述代码,我们可以观察到 myThread类 使用了 Runnable接口。这样我们就能在 myThread类 中重写 run方法 来创建一个线程。


2.1 创建Thread类实例

与继承 Thread类 来创建线程方法不同的是:如果 Runnable接口 要创建 Thread 类的实例,需要调用 Thread 的构造方法时要将 Runnable 接口类型的对象作为 target 参数。如下所示:

​
class myThread implements Runnable {
    @Override
    public void run() {
        System.out.println("Hello World");
    }
}
public class ThreadDemo {
    public static void main(String[] args) {
        Thread thread = new Thread(new myThread());//调用Thread的构造方法
        thread.start();//调用start方法
    }
}

​

 运行后输出:

通过上述代码以及输出结果,我们发现继承 Thread类 和实现 Runnable接口 除了创建 Thread类实例 不同外,都调用了 start方法 来启动线程。


总结:

  • 实现Runnable接口,必须重写run方法来创建线程
  • 如要通过Runnable接口创建Thread类引用,实例化Thread对象的时候必须将Runnable接口类的对象作为参数来实例化Thread对象
  • Ruannable接口和Thread类启动线程的方式都是通过start方法

3. 变种创建方式


3.1 匿名内部类

匿名内部类创建 Thread类 子类对象:

    public static void main(String[] args) {
        Thread thread = new Thread(){
            @Override
            public void run() {
                System.out.println("这是Thread类里的一个线程");
            }
        };
        thread.start();
    }

运行后输出:

通过上述代码,我们可以观察到。创建了 Thread类 子类对象也是要重写 Thread类 中的 run 方法并在 run 方法里面创建线程的。 


匿名内部类创建 Runnable接口 子类对象:

    public static void main(String[] args) {
        Runnable runnable = new Runnable() {
            @Override
            public void run() {
                System.out.println("这是Runnable接口下的一个线程");
            }
        };
        runnable.run();
    }

运行后输出:

创建 Runnable 接口的子类对象,也要重写 Runnable 接口底下的run方法才能创建线程。 


3.2 lambda表达式

lambda 表达式的基本写法为: () -> {}。lambda表达式是通过传参的形式创建子类对象。如使用 lambda 表达式创建一个 Thread 类 线程:

    public static void main(String[] args) {
        Thread thread = new Thread( () -> {
            System.out.println("这是lambda表达式下的一个线程");
        } );
        thread.start();
    }

运行后输出:


 当然我们可以通过循环的方式来观察线程的运行:

    public static void main(String[] args) {
        Thread thread = new Thread( () -> {
            int i = 1;
            while(true) {
                System.out.println("这是第"+i+"个线程");
                i++;
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                if (i == 7){
                    break;
                }
            }
        });
        thread.start();
    }

运行后输出:

总结:

  • 可通过匿名内部类来创建Thread类的子类对象、Runnable接口的子类对象,并重写run方法来创建一个线程
  • 可通过lambda表达式来创建线程
  • 线程的启动都是用start方法

以上就是创建线程的基本方法,当我们学到多线程进阶内容后。就会学到使用 Callable 接口、线程池、框架来创建线程。这些在我的后期内容会一一给大家展示!

🧑‍💻作者:程序猿爱打拳,Java领域新星创作者,阿里云社区博客专家。

🗃️文章收录于:Java多线程编程

🗂️JavaSE的学习:JavaSE

🗂️Java数据结构的学习: 数据结构与算法


本期博文到这里结束了,感谢点赞、收藏、关注~


http://www.kler.cn/a/18011.html

相关文章:

  • 【C++】一种针对代码的连续条件检查方案,累计布尔结果
  • 基于混合配准策略的多模态医学图像配准方法研究
  • Android OpenGL ES详解——立方体贴图
  • 移动端【01】面试系统的MVVM重构实践
  • 数据结构-集合
  • 【小程序】封装网络请求request模块
  • 【Linux】浅谈网络协议栈-网桥br0
  • 分布式锁Redisson对于(不可重入、不可重试、超时释放、主从一致性)四个问题的应对
  • Python人工智能—线性回归
  • C++面试题
  • java8新特性——StreamAPI
  • PyQt5零基础入门(二)——主窗口的显示与退出
  • LInux grep sed awk 命令详解
  • 开关电源基础01:电源变换器基础(3)
  • 数影周报:假冒ChatGPT的恶意软件激增,谷歌开启无密码登录
  • docker-mysql的几个问题
  • 学习HCIP的day.04
  • 【383. 赎金信】
  • 从零开始学习Linux运维,成为IT领域翘楚(十)
  • 【刷题】142. 环形链表 II
  • maven配置阿里云镜像仓库
  • 关于C语言的一些笔记
  • 算法:递归启蒙-汉诺塔
  • ChatGPT使用入门
  • 计算机网络基础知识(一)计算机发展史、网络设备、网络结构及拓扑
  • 设计模式:SOLID原则