Java 中线程的创建方式共有四种主流且官方支持的方式按演进顺序与能力维度可分为✅ 继承Thread类基础、耦合高✅ 实现Runnable接口解耦、推荐、无返回值✅ 实现CallableV接口 FutureTask或线程池支持返回值与异常✅ 使用线程池ExecutorService配合Runnable/Callable生产级首选以下从原理、代码实现、适用场景、优劣对比四维度系统展开一、四种创建方式核心对比创建方式是否可返回结果是否可抛出受检异常耦合度扩展性典型使用场景extends Thread❌ 否run()返回void❌ 否run()不声明throws⚠️ 高强制单继承❌ 差无法再继承其他类教学演示、简单逻辑implements Runnable❌ 否❌ 否✅ 低仅接口实现✅ 强可组合多个接口通用任务抽象如定时任务、事件处理器implements CallableVFutureTask/submit()✅ 是泛型V✅ 是call()可throws Exception✅ 低✅ 强与ExecutorService天然兼容需异步获取结果的任务如远程调用、计算密集型线程池Executors.newFixedThreadPool()等 Runnable/Callable✅ 支持两者✅ 支持Callable✅ 极低面向接口编程✅✅ 最强资源复用、拒绝策略、监控集成所有中高并发生产环境Web 请求处理、批量数据导入注Lambda 表达式本质是Runnable/Callable的语法糖不构成独立创建方式但显著提升可读性 。二、代码实现详解含关键注释1. 继承 Thread 类public class MyThread extends Thread { Override public void run() { System.out.println(Thread ID: getId() , Name: getName()); } } // 启动 new MyThread().start(); // 必须调用 start()而非 run()⚠️ 缺陷MyThread无法再继承其他业务类Thread类职责过重既是执行体又是线程载体。2. 实现 Runnable 接口推荐初阶解耦public class Task implements Runnable { private final String name; public Task(String name) { this.name name; } Override public void run() { System.out.println(Running task: name); } } // 启动解耦同一 Runnable 可被多个 Thread 复用 Thread t1 new Thread(new Task(A)); Thread t2 new Thread(new Task(B)); t1.start(); t2.start();✅ 优势避免 Java 单继承限制Runnable可作为纯任务契约被注入到任意执行上下文 。3. 实现 Callable Future 获取结果import java.util.concurrent.*; public class ComputeTask implements CallableInteger { private final int n; public ComputeTask(int n) { this.n n; } Override public Integer call() throws Exception { if (n 0) throw new IllegalArgumentException(n must 0); return fib(n); // 斐波那契计算示例 } private int fib(int n) { return n 1 ? n : fib(n-1) fib(n-2); } } // 方式 A通过 FutureTask 包装兼容老版 Thread FutureTaskInteger ft new FutureTask(new ComputeTask(10)); new Thread(ft).start(); System.out.println(Result: ft.get()); // 阻塞获取结果 // 方式 B线程池提交现代标准写法 ExecutorService es Executors.newSingleThreadExecutor(); FutureInteger future es.submit(new ComputeTask(10)); System.out.println(Async result: future.get()); // 支持超时future.get(3, TimeUnit.SECONDS) es.shutdown();✅ 关键价值Callable.call()返回泛型结果并可抛异常Future.get()提供结果同步/超时/取消能力 。4. 线程池生产环境唯一推荐方式ExecutorService pool Executors.newFixedThreadPool(4, r - { // 自定义 ThreadFactory设置名称与守护属性 Thread t new Thread(r, Worker- counter.incrementAndGet()); t.setDaemon(false); return t; }); ListFutureString futures new ArrayList(); for (int i 0; i 10; i) { final int taskId i; futures.add(pool.submit(() - { Thread.sleep(100); return Task- taskId done by Thread.currentThread().getName(); })); } // 批量收集结果体现 Future 的组合能力 futures.forEach(f - { try { System.out.println(f.get()); // 每个任务独立超时控制 } catch (Exception e) { e.printStackTrace(); } }); pool.shutdown();✅ 优势规避频繁创建/销毁线程开销提供队列缓冲、拒绝策略如AbortPolicy、可监控性Executors工厂方法覆盖Cached/Scheduled/WorkStealing等场景 。三、技术演进逻辑与选型建议阶段核心矛盾解决方案技术标志JDK 1.0–1.4线程即执行体逻辑与调度强绑定Thread继承start()/run()分离JDK 1.5任务What与执行者How需解耦Runnable/CallableExecutor框架java.util.concurrent包诞生现代微服务海量短生命周期任务、可观测性、弹性伸缩自定义线程池带ThreadFactoryRejectedExecutionHandlerCompletableFuture编排ForkJoinPool.commonPool()、virtual threadsJDK 21实际项目中95% 以上场景应直接使用ExecutorService.submit(Callable)辅以CompletableFuture.supplyAsync()进行异步编排彻底告别裸new Thread()。参考来源java中线程与任务的耦合性,Java创建多线程的几种方式详解-Fun言Java高级特性 - 多线程基础1使用线程第1关创建线程第2关使用 Callable 和 Future 创建线程三种线程创建方式的小案例Java并发编程——解析Thread类JUC (二) --------- Java 线程Java Thread源码分析