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

如何让Java程序等待Timer线程执行完毕后再继续运行?

解决Java主线程等待Timer任务完成的问题

嘿,我明白你遇到的问题了!当前代码里Timer是异步执行任务的,主线程调用currentClock.run()后不会停下来等它,直接就去打印text2了,这就是顺序不对的原因。另外wait()方法不能随便调用,它必须在同步代码块/方法里,而且当前线程得持有该对象的锁,否则就会抛出IllegalMonitorStateException,这也是你加了wait()却报错的原因。

下面给你两种可行的解决方案,适合不同的学习场景:

方案一:用CountDownLatch让主线程等待Timer任务结束

CountDownLatch是Java并发包里的工具类,专门用来让一个或多个线程等待其他线程完成操作。我们可以用它来监听clockHelper的任务是否完成:

import java.util.Timer;
import java.util.TimerTask;
import java.util.concurrent.CountDownLatch;

public class Main {
    public static void main(String[] args) throws InterruptedException {
        System.out.println("text1");
        Clock currentClock = new Clock();
        // 创建CountDownLatch,计数为1,代表等待1个任务完成
        CountDownLatch latch = new CountDownLatch(1);
        currentClock.run(latch);
        latch.await(); // 主线程在这里阻塞,直到latch的计数变为0
        System.out.println("text2");
    }
}

class ClockHelper extends TimerTask {
    private int actual = 0;
    private final CountDownLatch latch;

    // 构造方法传入latch,用于任务完成时通知主线程
    public ClockHelper(CountDownLatch latch) {
        this.latch = latch;
    }

    @Override
    public void run() {
        if (actual < 3) {
            System.out.println(".");
            actual++;
        } else {
            cancel();
            latch.countDown(); // 任务完成,将计数减为0,唤醒主线程
        }
    }
}

class Clock {
    public void run(CountDownLatch latch) {
        Timer watch = new Timer();
        TimerTask timer2 = new ClockHelper(latch);
        watch.schedule(timer2, 1000, 500);
    }
}

方案二:直接用主线程循环+Sleep(更简单直观)

如果只是学习场景,其实不用Timer这么复杂,直接在主线程里循环打印点,每次休眠指定时间,这样主线程自然会阻塞,顺序就完全符合你的预期了:

public class Main {
    public static void main(String[] args) throws InterruptedException {
        System.out.println("text1");
        // 先等待1秒,再循环打印3个点,每个点间隔500ms
        Thread.sleep(1000);
        for (int i = 0; i < 3; i++) {
            System.out.println(".");
            Thread.sleep(500);
        }
        System.out.println("text2");
    }
}

为什么之前的wait()没用?

再补充一下IllegalMonitorStateException的原因:当你调用obj.wait()时,必须先通过synchronized(obj)获取该对象的锁,比如:

synchronized(currentClock) {
    currentClock.wait();
}

但就算你这么写了,还需要其他线程调用currentClock.notify()或notifyAll()来唤醒它,不然主线程会一直等下去。所以对于你的场景,CountDownLatch是更合适的工具。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.14 07:53:37