事情似乎在并行运行Java

事情似乎在并行运行Java,java,android,android-studio,runnable,Java,Android,Android Studio,Runnable,我对Java相当陌生;(如果要阻止当前线程,应该使用Thread.sleep(500)静态方法而不是计时器。Android的主线程看起来有点像 while (true) { Runnable nextThingToDo = getNextTaskFromQueue(); nextThingToDo.run(); } 和Handlers用于将新任务放入队列。您在on???方法(如Activity#onCreate上写入的所有代码也是此类任务的一部分。触摸事件处理和屏幕绘图更新等内

我对Java相当陌生;(如果要阻止当前线程,应该使用Thread.sleep(500)静态方法而不是计时器。

Android的主线程看起来有点像

while (true) {
    Runnable nextThingToDo = getNextTaskFromQueue();
    nextThingToDo.run();
}
Handler
s用于将新任务放入队列。您在
on???
方法(如
Activity#onCreate
上写入的所有代码也是此类任务的一部分。触摸事件处理和屏幕绘图更新等内容也会出现在该队列中。因此,您必须永远不要暂停该线程,这是唯一的方法s“later”是为以后排队(队列不是简单的先进先出队列,它支持延迟等)

现在,您的
计时器
任务
可运行
调度为在设置的延迟后运行。由于调用
处理程序.postDelayed
的代码必然已经在这样的可运行本身中,因此需要在队列执行并运行
任务之前执行该操作。因此,展开的while循环中发生的事情是粗糙的y

Runnable nextThingToDo = getNextTaskFromQueue(); 
nextThingToDo.run();
// inside above "run"... whatever code path leads to turnend()
    if (leftover == 0) {
        housenumber = 1;
        Runnable r = construct();// it's only a reference to a `Runnable` object, nothing executes here
        t = new Timer(r, 500, true);
        // inside Timer
            handler.postDelayed(task, 500); // task is now in the queue
    }
    //code 2 -- it actually runs now.
// whatever else is in your code on the way out from "turnend()"

// ... things happen, 500ms passes

Runnable nextThingToDo = getNextTaskFromQueue(); // this is the `task` object
nextThingToDo.run();
// inside this "run"
    if (!paused) {
        runnable.run (); // this is the `r` object
        // inside task
           {
            // code1 -- running ~ 500ms after code2
            if (housenumber == 8) {
                t.stopTimer();
            }
          }
要解决您的问题,您首先应该了解,编写随时间分多个步骤进行的代码并不简单,需要编写代码,以便代码始终触发未来的代码,这是一系列无休止的事件。代码不能等待未来的任务完成,您只能告诉未来的代码您希望在其上执行的操作特朗普:完成了

例如,通过将代码物理地移动到它所属的位置:

public void turnend() {
    if (leftover == 0) {
        housenumber = 1;
        Runnable r = new Runnable() {
            @Override
            public void run() {
                //code1
                if (housenumber == 8) {
                    t.stopTimer();
                }
                //code 2
            }
        };
        t = new Timer(r, 500, true);
    }
}
或者,通过向将来的代码提供对您希望调用的代码的引用,这就是所谓的“回调”。最简单的形式是:

    public void turnend() {
        final Runnable callback = new Runnable() {
            @Override
            public void run() {
                //code 2
            }
        };

        if (leftover == 0) {
            housenumber = 1;
            Runnable r = new Runnable() {
                @Override
                public void run() {
                    //code1
                    if (housenumber == 8) {
                        t.stopTimer();
                    }
                    callback.run();
                }
            };
            t = new Timer(r, 500, true);
        }
    }
每次你想写的时候

    public void things() {
        // code 1
        // delay of 500
        // code 2
    }
相反,大致做到:

    public void thingsPart1() {
        // code1

        handler.postDelayed(new Runnable() {
            @Override
            public void run() {
                thingsPart2();
            }
        }, 500);
    }

    public void thingsPart2() {
        // code 2
    }

一个可运行的对象在它自己的线程上运行。当计时器结束时,你可以使用回调runOnUiThread@Striker是的。但我想等待Runnable。我刚刚读到了回调,它似乎只是在计时器结束时回调。因此,它不等待计时器。如果我错了,请纠正我。为什么要等待它?您可以在“代码2”之后执行
run
方法中的代码。此外,这个
Timer
类是什么?它/它是否启动
线程
(用于并行运行代码)?似乎既不是
java.util.Timer
也不是
javax.swing.Timer
,而且我不知道android中内置了一个。@zapl嗨,我已经编辑了我的帖子。Timer类正是我昨天问的另一个问题()。我想等待,因为我在代码2中有一些东西依赖于代码1。啊哈。谢谢。我不知道“线程”。我会读更多关于它的内容。欢迎更多解释:)@Seung但是,不要在Android的主线程中使用
sleep
(解释了一点),它只会暂时冻结应用程序(包括所有动画,不要对触摸做出反应等)。你需要使用类似的东西才能获得正确的效果。我刚刚看到了你的编辑,我还以为你使用的是Java API中的计时器()@zapl我来看看。谢谢你的提示!@oilal抱歉混淆:/Brilliant!非常感谢。:)
    public void things() {
        // code 1
        // delay of 500
        // code 2
    }
    public void thingsPart1() {
        // code1

        handler.postDelayed(new Runnable() {
            @Override
            public void run() {
                thingsPart2();
            }
        }, 500);
    }

    public void thingsPart2() {
        // code 2
    }