Java | 线程的三种创建和启动方式

大家好,我是程序员影子

一名致力于帮助更多朋友快速入门编程的程序猿

今天来聊一聊关于Java 中的线程的三种创建和启动方式

一、通过继承 Thread

这是最直接的方式,通过创建一个新的类,继承自Thread类,并重写run()方法。然后创建该类的实例,并调用start()方法来启动线程。

csharp 复制代码
class MyThread extends Thread {
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("MyThread: " + i);
        }
    }
}
public class CreateThreadByExtendingExample {
    public static void main(String[] args) {
        MyThread t1 = new MyThread();
        t1.start(); // 启动线程
    }
}

二、通过实现 Runnable接口

这是推荐的方式,通过创建一个新的类,实现Runnable接口,并实现run()方法。然后将该类的实例传递给Thread对象,并调用start()方法来启动线程。

typescript 复制代码
class MyRunnable implements Runnable {
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("MyRunnable: " + i);
        }
    }
}
public class CreateRunnableExample {
    public static void main(String[] args) {
        Thread t2 = new Thread(new MyRunnable());
        t2.start(); // 启动线程
    }
}

三、通过 Executor框架和 Callable接口

  • Callable接口与Runnable类似,但它有一个call()方法,该方法在执行线程任务时可以返回结果或抛出异常。
  • Executor框架是Java 5引入的,用于管理线程池。它允许你提交RunnableCallable任务,而不需要直接管理线程。
java 复制代码
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
class MyCallable implements Callable<Integer> {
    public Integer call() {
        int sum = 0;
        for (int i = 1; i <= 10; i++) {
            sum += i;
        }
        return sum;
    }
}
public class CallableExample {
    public static void main(String[] args) {
        ExecutorService executor = Executors.newFixedThreadPool(10);
        Future<Integer> future = executor.submit(new MyCallable());
        try {
            Integer result = future.get(); // 获取异步执行的结果
            System.out.println("异步计算结果:" + result);
        } catch (Exception e) {
            e.printStackTrace();
        }
        executor.shutdown(); // 关闭线程池
    }
}

在这个例子中,我们创建了一个Callable任务,它计算1到10的整数和。然后我们使用ExecutorServicesubmit()方法来提交这个任务,并获取一个Future对象。通过Future对象的get()方法,我们可以等待任务完成并获取结果。

以上三种方式都可以创建和启动线程,但实现Runnable接口的方式更为灵活,并且Executor框架提供了更高级的线程管理功能,可以更好地控制线程池的大小和管理线程的生命周期。

以上就是本次分享的所有内容,感兴趣的朋友点个关注呀,感谢大家啦~

更多Java | AI+编程玩法 的相关资料和源码请移步至公众号:程序员影子

相关推荐
前期后期6 分钟前
设计模式:为什么使用模板设计模式(不相同的步骤进行抽取,使用不同的子类实现)减少重复代码,让代码更好维护。
java·前端·设计模式
苹果酱05677 分钟前
KisFlow-Golang流式实时计算案例(四)-KisFlow在消息队列MQ中的应用
java·vue.js·spring boot·mysql·课程设计
ps酷教程13 分钟前
tomcat构建源码环境
java·tomcat
云闲不收16 分钟前
垃圾回收——三色标记法(golang使用)
jvm·算法·golang
[email protected]24 分钟前
ASP.NET Core Web API 参数传递方式
后端·asp.net·.netcore
菜鸟江多多25 分钟前
32x32热成像高斯滤波图像处理
图像处理·单片机·算法
秋野酱26 分钟前
基于SpringBoot酒店管理系统设计和实现(源码+文档+部署讲解)
java·spring boot·后端
阳洞洞35 分钟前
二叉树的层序遍历
数据结构·算法·leetcode·二叉树遍历·广度优先搜索
今天也要早睡早起36 分钟前
代码随想录算法训练营Day32| 完全背包问题(二维数组 & 滚动数组)、LeetCode 518 零钱兑换 II、377 组合总数 IV、爬楼梯(进阶)
数据结构·c++·算法·leetcode·动态规划·完全背包
在下木子生38 分钟前
mac如何将jar包上传到maven中央仓库中
java·macos·maven·jar