Лучший способ рассчитать ETA операции? - PullRequest
14 голосов
/ 12 мая 2009

Я ищу лучший способ рассчитать ETA операции (IE: загрузка файла), используя информацию о линейном ходе.

Допустим, у меня есть следующий метод, который вызывается:

void ReportProgress(double position, double total)
{
    ...
}

У меня есть пара идей:

  • рассчитать прогресс за определенный промежуток времени (например, за последние 10 с) и использовать эту скорость в качестве средней скорости для операции
  • сохранить набор последних x прогрессов, о которых было сообщено, вычислить скорость каждого приращения и использовать среднее значение

Ответы [ 8 ]

7 голосов
/ 12 мая 2009

Я на самом деле презираю обе эти идеи, потому что они оба укусили меня как разработчика.

Первый не учитывает ситуацию, когда операция действительно ускоряется, он говорит, что осталось 10 минут, и я возвращаюсь после 3, и все закончено.

Второе не учитывает замедление операции - я думаю, что проводник Windows должен использовать этот метод, так как всегда кажется, что копирование 90% файлов всегда занимает 90%, а затем копирование - еще 90% времени что последние 10% файлов: -).

Я давно привык вычислять и усреднять эти цифры. Клиентов это не волнует (они на самом деле тоже не заботятся о двух других вариантах, они просто хотят видеть некоторый прогресс), но это заставляет меня чувствовать себя лучше, и это действительно все, что меня волнует конец дня; -)

6 голосов
/ 12 мая 2009

Примерно так должно получиться:

void ReportProgress(double position, double total)
{
    static TimeType startTime;

    if (position == 0)
    {
        startTime = GetTime();
        return; // to avoid a divide-by-zero error
    }

    TimeType elapsedTime = GetTime() - startTime;
    TimeType estimatedRemaining = elapsedTime * total / position;
    TimeType estimatedEndTime = GetTime() + estimatedRemaining;

    // Print the results here
}

Оценка приближается к истине, когда прогресс приближается к 100%

4 голосов
/ 03 июня 2009

Брэм Коэн немного об этом говорил. Он приложил немало усилий к вычислениям ETA в BitTorrent (однако в своем выступлении он упомянул, что еще никто не подошел к нему и не сказал «эй! Великолепные вычисления ETA в bittorrent man!»). Это не простая проблема.

Некоторые соответствующие ссылки:

4 голосов
/ 12 мая 2009

Я думаю, что эта проблема в значительной степени неразрешима, но можно создать некоторые точные оценки с немного большим знанием процесса, который выполняется. А в тех случаях, когда есть большие неизвестные, лучше информировать пользователей об этих неизвестных, чтобы они могли их учитывать.

Чтобы взять простой пример загрузки пакета файлов, у вас есть две известные переменные:

  • Количество файлов
  • Размер файлов

Для каждого файла есть постоянные издержки (время, необходимое для установления соединения, и время, необходимое для открытия файла в файловой системе). Существует также очевидное время загрузки, связанное с размером файлов. Создание функции, которая может выражать это как оставшееся время с точки зрения текущей скорости загрузки, является простым и точным, если скорость загрузки не колеблется слишком сильно. Но в этом и заключается проблема.

С точной моделью операции, которую вы выполняете, легко предсказать, сколько времени это займет, если нет внешних воздействий. И это редко возможно.

Однако вы могли бы пойти на решение, которое пытается понять и объяснить эти внешние влияния. Пользователь может оказаться полезным получать оповещения, когда скорость резко меняется, поскольку он может скорректировать свои планы в соответствии с новым ETA. Также может быть полезно объяснить, какие факторы влияют на текущую операцию. например,

Your download will complete in 6 minutes, if the download speed stays at 50k/s

Это позволяет пользователю делать некоторые обоснованные предположения, если он знает, что скорости могут измениться. И в конечном итоге приводит к меньшему количеству разочарований.

1 голос
/ 30 августа 2013

В Python:

>>> done=0.3; duration=10; "time left: %i" % (duration/done-duration)
'time left: 23'
1 голос
/ 12 мая 2009

Если вам нужен ETA, а не «индикатор выполнения», можете ли вы указать более одной цифры?

Рассчитайте среднюю скорость загрузки за заданный период времени (в зависимости от того, как долго может длиться общая загрузка, если вы смотрите на 10+ минут, то каждые 5 секунд или около того будет в порядке) и сохраняйте запись средние.

Затем вы можете предоставить две цифры, верхнюю и нижнюю оценки.

Если вы уверены, что средние значения будут хорошим показателем общего времени загрузки, то вы можете отобразить 40-й процентиль и 60-й - если среднее время загрузки сильно различается, то 10-й и 90-й могут быть лучше.

Я бы предпочел увидеть приблизительный интервал «21-30 минут», и он будет точнее, чем 29 минут 35,2 секунды, и он будет в нескольких милях и сильно варьируется от одного обновления к другому.

0 голосов
/ 05 декабря 2018

Я работал над проектом, для которого требовалось ETA из-за долгих и трудоемких вычислений, и в итоге я разбил процесс на партии одинакового размера. Затем я определяю время, необходимое для вычисления каждого пакета, и добавляемое время добавляется в список FIFO прошедших вычислений.

Время в списке затем усредняется, а полученное время умножается на количество оставшихся партий.

number of batches = N
size of batch = x
past computations length = l (t0,t1,...,tl)
avg time per batch = (t0 + t1 + ... + tl) / l = t
computed batches = n

ETA = t * (N - n)

Обратите внимание , что список имеет фиксированную длину, которая должна быть достаточно длинной, чтобы процесс оценки "помнил" и соответствовал возможным пикам в вычислениях, но он также должен быть коротким достаточно, чтобы быстро адаптироваться к изменениям скорости вычислений (например, больше времени вычислений после окончания конкурирующей задачи / большая пропускная способность)

0 голосов
/ 12 мая 2009

Это будет зависеть от того, насколько согласован режим работы. Если это соответствует, было бы разумно использовать среднее время предыдущих операций. Если это не так, вам лучше синхронизировать текущую операцию и экстраполировать.

Редактировать: Если операция несовместима с предыдущими запусками, а также несовместима с начала до конца, значит, у вас есть неразрешимая проблема. Предсказывать непредсказуемое всегда весело :) 1005 *

Вы можете заранее решить, хотите ли вы недооценить или переоценить, и добавить коэффициент оценки к оценке. Например, если вы хотите переоценить, и первые 10% занимают 6 секунд, вы можете экстраполировать до 60 секунд, а затем умножить на 1,5, чтобы получить общую оценку 90 секунд. По мере того как процент выполнения увеличивается, уменьшайте коэффициент помадки, пока на уровне 100% он не станет 1,0.

...