Как построить секундомер с сотой секундной точности? - PullRequest
0 голосов
/ 16 апреля 2020

Я пытаюсь построить секундомер с сотней секундной точности. У меня есть этот код, который выполняется каждые 10 миллисекунд, но у меня возникают проблемы при преобразовании его в формат 0 (мин): 0 (se c): 00.

timer.post(new Runnable() {
    @Override
    public void run() {
        time += 1;
        txtView.setText(convertTimeToText(time));
        timer.postDelayed(this, 10);
    }
});

private String convertTimeToText(int time) {
    String convertedTime = time / 6000 + ":" + (time / 100) % 60
            + ":" + (time / 10) % 10 + time % 10;
    return convertedTime;
}

Мне нужна помощь с convertTimeToText ( int time) {}, который форматирует время.

EDIT: Спасибо Ole VV и W JS за форматирование ответа и за то, как исправить задержку, которую я имел, это код, который я придумал, если кто-нибудь это нужно, пока это работает хорошо, возможно использование System.nanoTime () даст вам более точные результаты, но для моего использования это хорошо.

public void start(){
        final long timeMillisWhenStarted = System.currentTimeMillis();
        if(!isRunning){
            isRunning = true;
            timer.post(new Runnable() {
                @Override
                public void run() {
                     long millisNow = System.currentTimeMillis();
                     long time = millisNow - timeMillisWhenStarted;
                    yourtxtView.setText(convertTimeToText(time));
                    timer.postDelayed(this, 10);
                }
            });
        }
    }

private String convertTimeToText(long time){
        long hundredths = time  / 10;
        long sec = hundredths / 100;
        long min = sec / 60;

        return String.format("%02d:%02d.%02d", min % 60, sec % 60, hundredths % 100);

        }

Ответы [ 2 ]

2 голосов
/ 17 апреля 2020

Использовать стандартную библиотеку

Ваш таймер не точный. Ваша наблюдаемая задержка происходит оттуда. Каждый раз считывайте время с некоторых часов, а не добавляйте 1/100 секунды. Используйте, например, System.currentTimeMillis(), System.nanoTime() или Instant.now(). Сохраните показания с момента запуска вашего секундомера и вычтите для получения текущего значения секундомера.

Если выполнение системного вызова 100 раз в секунду будет слишком дорогим (что я не ожидаю), сделайте это, например, для каждые 30 тиков, чтобы настроить секундомер обратно на правильное время.

Далее, если вы используете Java 9 или выше, используйте класс Duration для преобразования времени (в миллисекундах или наносекундах) до минут и секунд. Если вы выполняете преобразование вручную, как пытались, оно подвержено ошибкам и трудно читается, что, как я полагаю, стало одной из причин вашего вопроса.

Например:

    long millisNow = System.currentTimeMillis();
    Duration time = Duration.ofMillis(millisNow - timeMillisWhenStarted);

    String convertedTime = String.format("%d:%02d.%02d",
            time.toMinutes(), time.toSecondsPart(), time.toMillisPart() / 10);
2 голосов
/ 16 апреля 2020

Посмотрите, поможет ли это. Остатки вычислялись неправильно.

  • Для 12340 hundreds секунд это будет 123.40 seconds
  • , поэтому 12340 / 6000 = 2 для минут
  • 12340 % 6000 получает то, что осталось, 340
  • , поэтому 340 /100 = 3 секунд
  • оставляя 340 % 100 = 40 сотых
public static void main(String[] args) {
    // n = 16 mins 4 seconds and 99 hundredths
    int n = (16 * 6000) + (4 * 100) + 99;
    System.out.println(convertTimeToText(n));
}

private static String convertTimeToText(int time) {
    int mins = time / 6000;
    time %= 6000; // get remaining hundredths
    int seconds = time / 100;
    int hundredths = time %= 100; // get remaining hundredths

    // format the time.  The leading 0's mean to pad single
    // digits on the left with 0.  The 2 is a field width
    return String.format("%02d:%02d:%02d", mins, seconds,
            hundredths);
}

Это печатает

16:04:99
...