You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java如何创建后台运行的定时器 同时不阻塞用户正常交互操作

Java 非阻塞后台定时更新股价实现方案

核心实现逻辑

使用Java标准库自带的ScheduledExecutorService实现定时任务,该工具会在独立的后台线程池运行调度任务,和处理用户交互的主线程完全隔离,不会阻塞用户操作,也不需要手动编写sleep逻辑处理间隔。

可直接运行的示例代码

import java.util.Random;
import java.util.Scanner;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

public class StockGame {
    // 用volatile修饰保证多线程访问的可见性,后台更新后主线程能立刻读到最新价格
    private static volatile double stockPrice = 100.0;
    // 随机数生成器,用来模拟股价波动
    private static final Random random = new Random();

    public static void main(String[] args) {
        // 初始化单线程的定时调度器,足够应对小型课程项目需求
        ScheduledExecutorService executor = Executors.newSingleThreadScheduledExecutor();
        
        // 提交定时任务:初始0延迟后开始执行,每隔10秒执行一次股价更新
        executor.scheduleAtFixedRate(() -> {
            // 模拟股价在±5%范围内随机波动,你可以替换成自己的股价更新逻辑
            double changeRate = 0.95 + random.nextDouble() * 0.1;
            stockPrice = Math.round(stockPrice * changeRate * 100) / 100.0;
            // 测试用,可以删掉这行打印
            System.out.printf("\n[系统通知] 股价已更新,当前价格:%.2f\n", stockPrice);
        }, 0, 10, TimeUnit.SECONDS);

        // 主线程处理用户输入,完全不受后台定时任务影响
        Scanner scanner = new Scanner(System.in);
        while (true) {
            System.out.print("\n请输入操作(1查看股价,2退出):");
            int op = scanner.nextInt();
            if (op == 1) {
                System.out.printf("当前股价:%.2f\n", stockPrice);
            } else if (op == 2) {
                // 退出前关闭调度器,释放线程资源
                executor.shutdown();
                System.out.println("程序退出");
                break;
            } else {
                System.out.println("无效操作,请重新输入");
            }
        }
        scanner.close();
    }
}

上面的代码可以直接在repl.it上运行,后台每10秒自动更新股价,主线程随时可以响应用户输入,不会出现阻塞。

注意事项

  • 跨线程共享的股价变量必须加volatile修饰,避免后台线程更新后主线程读取到旧值的可见性问题
  • 如果后续需要实现暂停更新、调整更新间隔的需求,可以接收scheduleAtFixedRate方法返回的ScheduledFuture对象,调用cancel()方法取消现有任务后重新提交新的调度任务即可
  • 课程项目场景下单线程调度器足够使用,如果后续需要扩展多支股票的并行更新,可以换成Executors.newScheduledThreadPool(n)指定线程池大小,n为需要并行处理的股票数量

学习资源

直接查阅JDK官方文档中java.util.concurrent.ScheduledExecutorService相关章节即可,标准库文档包含完整的方法说明和使用示例,足够掌握该工具的所有常用用法。

内容的提问来源于stack exchange,提问作者Jared

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 14:15:02