Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/336.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么我的Android倒计时这么慢?_Java_Android_Timer - Fatal编程技术网

Java 为什么我的Android倒计时这么慢?

Java 为什么我的Android倒计时这么慢?,java,android,timer,Java,Android,Timer,我正在尝试在安卓系统中制作一个倒计时器,用于一个小型安卓应用程序。应用程序将从秒数倒计时到0,然后执行一些操作。我正在使用android.os.countdowntimer提供的countdowntimer。这是我的密码: /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInst

我正在尝试在安卓系统中制作一个倒计时器,用于一个小型安卓应用程序。应用程序将从秒数倒计时到0,然后执行一些操作。我正在使用android.os.countdowntimer提供的countdowntimer。这是我的密码:

/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.quizlayout);

    new CountDownTimer(30000, 1000) {

        TextView tx = (TextView) findViewById(R.id.textView2);

         public void onTick(long millisUntilFinished) {
             tx.setText("seconds remaining: " + millisUntilFinished / 1000);
         }

         public void onFinish() {
             tx.setText("done!");
         }
      }.start();
}
然而,这个倒计时器真的很慢。计时器倒计时一秒大约需要3秒的实时时间。我想知道发生了什么事?我上面的代码或多或少是直接从google()复制的

有谁能帮我解释一下为什么我的计时器这么慢,并提供一种方法让它快一点吗


(编辑):我在英特尔atom x86模拟器上运行此功能。我正在模拟android 2.3.3环境。

根据android倒数计时器文档

对onTick(long)的调用与此对象同步,以便在上一次回调完成之前不会发生对onTick(long)的调用。这仅在onTick(long)的实现需要比倒计时间隔更长的执行时间时才相关

看看这个倒计时计时器的例子

或者,您可以生成一个新线程,让该线程在您想要的时间间隔内睡眠,并在它醒来时采取行动,反之亦然


您还可以根据Android倒数计时器文档来设置计时器任务

对onTick(long)的调用与此对象同步,以便在上一次回调完成之前不会发生对onTick(long)的调用。这仅在onTick(long)的实现需要比倒计时间隔更长的执行时间时才相关

看看这个倒计时计时器的例子

或者,您可以生成一个新线程,让该线程在您想要的时间间隔内睡眠,并在它醒来时采取行动,反之亦然


您还可以使用将发布相同runnable的处理程序来处理timertask。这将消除对额外线程的需要:

Handler handler=new Handler();
handler.postRunnable(... , 1000) ;

在runnable中,再次为同一处理程序调用postRunnable(并添加何时停止的条件)。

使用将发布相同runnable的处理程序。这将消除对额外线程的需要:

Handler handler=new Handler();
handler.postRunnable(... , 1000) ;

在runnable中,再次调用同一处理程序的postRunnable(并添加一个何时停止的条件)。

无论ui更新性能如何,CountDownTimer都是无效的。对于完美的ui更新,最好创建自定义倒计时。我自己做的,所以在这里。它在我的应用程序上是完美的

public abstract class CountDown {

int totalTime = 0;
int tickTime = 0;

Thread thread;
boolean canceled = false;

public CountDown(int totalTime,int tickTime){
    this.totalTime = totalTime;
    this.tickTime = tickTime;
}

public abstract void onTick();

public abstract void onFinish();

public void start(){

    thread = new Thread(new Runnable() {

        @Override
        public void run() {
            // Do in thread

            canceled = false;

            for (int elapsedTime = 0; elapsedTime < totalTime; elapsedTime += tickTime) {

                if(!canceled){

                        onTick();
                        try {
                            thread.sleep(tickTime);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }

                }else{
                    break;
                }
            }

            if(!canceled){
                onFinish();
            }

        }

    });

    thread.start();
}

public void cancel(){
    canceled = true;
}
}

无论ui更新性能如何,倒计时都是无效的。对于完美的ui更新,最好创建自定义倒计时。我自己做的,所以在这里。它在我的应用程序上是完美的

public abstract class CountDown {

int totalTime = 0;
int tickTime = 0;

Thread thread;
boolean canceled = false;

public CountDown(int totalTime,int tickTime){
    this.totalTime = totalTime;
    this.tickTime = tickTime;
}

public abstract void onTick();

public abstract void onFinish();

public void start(){

    thread = new Thread(new Runnable() {

        @Override
        public void run() {
            // Do in thread

            canceled = false;

            for (int elapsedTime = 0; elapsedTime < totalTime; elapsedTime += tickTime) {

                if(!canceled){

                        onTick();
                        try {
                            thread.sleep(tickTime);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }

                }else{
                    break;
                }
            }

            if(!canceled){
                onFinish();
            }

        }

    });

    thread.start();
}

public void cancel(){
    canceled = true;
}
}

这是在真实设备上还是在模拟器上?GUI线程上是否有长任务运行?这可能会延迟对onTick的调用。我在GUI线程上没有其他任何东西。这个计时器几乎就是它。emulator+intel atom就是发生这种情况的原因。@user1116858:从您的编辑中可以看出,您正在一个模拟器上运行它-我在评论中问这个问题有一个特殊的原因。在真实的设备上尝试。这是在真实的设备上还是在模拟器上?GUI线程上是否有长任务运行?这可能会延迟对onTick的调用。我在GUI线程上没有其他任何东西。这个计时器几乎就是它。emulator+intel atom就是发生这种情况的原因。@user1116858:从您的编辑中可以看出,您正在一个模拟器上运行它-我在评论中问这个问题有一个特殊的原因。在真实的设备上尝试。我需要伪造ProgersBar更新,此方法比倒计时运行得更平滑。我需要伪造ProgersBar更新,此方法比倒计时运行得更平滑。该示例的链接已过期。该示例的链接已过期。谢谢,此方法对于更新UI非常有效。谢谢,这一个就像是更新UI的魅力。