Головна » як » Чому прогрес прогрес є таким неточним?

    Чому прогрес прогрес є таким неточним?

    На перший погляд, здається, що створення точної оцінки часу має бути досить простим. Зрештою, алгоритм, що виробляє індикатор виконання, знає всі завдання, які він повинен виконати заздалегідь ... правильно?

    Здебільшого, це правда, що алгоритм джерела знає, що потрібно робити заздалегідь. Однак, закріплення часу, необхідного для виконання кожного кроку, є дуже важким, якщо не практично неможливим завданням.

    Всі завдання не створені рівними

    Найпростішим способом реалізації індикатора є використання графічного представлення лічильника завдань. Де відсоток завершення просто обчислюється як Виконані завдання / Загальна кількість завдань. Хоча при першій думці це має логічний сенс, важливо пам'ятати, що (очевидно) деякі завдання займають більше часу.

    Розглянемо наступні завдання, які виконує інсталятор:

    1. Створити структуру папок.
    2. Розпакуйте та скопіюйте файли вартістю 1 ГБ.
    3. Створити записи реєстру.
    4. Створити записи меню початку.

    У цьому прикладі кроки 1, 3 і 4 завершаться дуже швидко, тоді як етап 2 займе деякий час. Таким чином, індикатор, що працює на простому рахунку, буде дуже швидко підскочити до 25%, трохи затриматись, а крок 2 працюватиме, а потім перейти до 100% майже відразу.

    Цей тип реалізації є насправді досить поширеним серед прогресуючих барів, оскільки, як зазначалося вище, його легко реалізувати. Однак, як ви можете бачити, вона підпорядкована непропорційним завданням, що перекручують фактичний відсоток прогресу, що стосується часу, що залишився.

    Для того, щоб обійти цю проблему, деякі індикатори виконання можуть використовувати реалізації, де кроки зважуються. Розгляньте кроки, наведені вище, де відносна вага призначається кожному кроку:

    1. Створити структуру папок. [Вага = 1]
    2. Розпакуйте та скопіюйте файли вартістю 1 ГБ. [Вага = 7]
    3. Створити записи реєстру. [Вага = 1]
    4. Створити записи меню початку. [Вага = 1]

    Використовуючи цей метод, індикатор ходу рухатиметься з кроком 10% (як загальна вага 10) з кроками 1, 3 і 4, переміщуючи планку 10% після завершення і кроком 2 переміщуючи його на 70%. Хоча, звичайно, не досконалі, такі способи є простим способом додати трохи більшу точність до відсотка прогресу.

    Попередні результати не гарантують майбутньої ефективності

    Розглянемо простий приклад того, що я прошу вас порахувати до 50, коли я використовую секундомір, щоб відзначити час. Припустимо, ви вважаєте до 25 за 10 секунд. Було б доцільно припустити, що ви будете рахувати інші цифри протягом додаткових 10 секунд, так що відстеження цього індикатора покаже 50% завершення, залишивши 10 секунд.

    Як тільки ваш рахунок досягне 25, я починаю кидати на вас тенісні м'ячі. Швидше за все, це порушить ваш ритм, оскільки ваша концентрація перейшла від строго підрахунку чисел до ухилення від кульок, що кидаються. Припускаючи, що ви можете продовжувати підрахунок, ваш темп, звичайно, трохи уповільнився. Так що тепер індикатор продовжує рухатися, але набагато повільніше, з розрахунковим часом, що залишився або зупинився, або фактично піднявся вище..

    Для більш практичного прикладу розглянемо завантаження файлу. Ви зараз завантажуєте файл розміром 100 МБ зі швидкістю 1 Мб / с. Це дуже легко визначити розрахунковий час завершення. Але 75% шляху там, деякі перевантаження мережі вражає, і ваша швидкість завантаження падає до 500 Кб / с.

    Залежно від того, як браузер обчислює час, що залишився, ваш ETA може миттєво перейти від 25 секунд до 50 секунд (використовуючи лише поточний стан: Розмір Останнє / Швидкість завантаження), або, найімовірніше, браузер використовує алгоритм ковзного середнього, який пристосував би коливання швидкості передачі без показу драматичних переходів користувачеві.

    Приклад алгоритму прокатки щодо завантаження файлу може працювати приблизно так:

    • Швидкість передачі даних за попередні 60 секунд запам'ятовується з найновішим значенням, яке замінює найстаріше (наприклад, 61-е значення замінює перше).
    • Ефективна швидкість передачі для цілей розрахунку - це середня величина цих вимірів.
    • Залишок часу розраховується як: Розмір залишився / ефективна швидкість завантаження

    Таким чином, використовуючи наш сценарій вище (заради простоти ми будемо використовувати 1 МБ = 1000 КБ):

    • Через 75 секунд завантаження, всі 60 збережених значень становитимуть 1000 Кб. Ефективна швидкість передачі - 1000 Кб (60 000 Кб / 60), яка дає час, що залишився, 25 секунд (25 000 Кб / 1000 Кб).
    • Через 76 секунд (коли швидкість передачі зменшується до 500 КБ) ефективна швидкість завантаження стає ~ 992 Кб (59,500 Кб / 60), що дає час, що залишився ~ 24,7 секунди (24,500 Кб / 992 Кб).
    • На 77 секундах: ефективна швидкість = ~ 983 Кб (59 000 кб / 60), що дає час, що залишився ~ 24,4 секунди (24 000 кб / 983 кб).
    • На 78 секундах: ефективна швидкість = 975 кб (58500 кб / 60), що дає час, що залишився ~ 24,1 секунди (23,500 кб / 975 кб).

    Ви можете бачити шаблон, що виникає тут, як падіння швидкості завантаження повільно вбудовується в середнє значення, яке використовується для оцінки часу, що залишився. За цим методом, якщо провал тривав лише 10 секунд, а потім повернувся на 1 Мб / с, користувач навряд чи помітить різницю (за винятком дуже незначного зриву у відліку розрахункового часу).

    Як дістатися до латунних гвинтів - це просто методологія для передачі інформації кінцевому користувачеві для фактичної основної причини ...

    Ви не можете точно визначити те, що є недетермінованим

    У кінцевому рахунку, неточність прогрессу зводиться до того, що він намагається визначити час для того, що є недетермінованим. Оскільки комп'ютери обробляють завдання як за запитом, так і у фоновому режимі, практично неможливо знати, які системні ресурси будуть доступні в будь-який момент у майбутньому - і це доступність системних ресурсів, необхідних для виконання будь-якого завдання.

    Припустимо, що ви виконуєте оновлення програми на сервері, який виконує досить інтенсивне оновлення бази даних. Під час цього процесу оновлення користувач потім надсилає запит до іншої бази даних, що працює на цій системі. Тепер серверні ресурси, спеціально для бази даних, повинні обробляти запити як для вашого оновлення, так і для ініційованого користувачем запиту - сценарій, який, безумовно, буде згубним для часу виконання. З іншого боку, користувач може ініціювати запит на передачу великих файлів, який би оподатковував пропускну здатність зберігання, що також зменшує продуктивність. Або заплановане завдання може стартувати, що виконує процес інтенсивної пам'яті. Ви отримаєте ідею.

    Як, можливо, більш реалістичний приклад для повсякденного користувача - слід запустити Windows Update або перевірку на віруси. Обидві ці операції виконують ресурсомісткі операції у фоновому режимі. Як наслідок, прогрес, який робить кожен, залежить від того, що користувач робить у той час. Якщо ви читаєте свою електронну пошту під час її запуску, швидше за все, попит на системні ресурси буде низьким, і індикатор виконання буде рухатися послідовно. З іншого боку, якщо ви робите редагування графіки, то ваш попит на системні ресурси буде набагато більшим, що призведе до шизофренії руху індикатора..

    В цілому, це просто, що немає кришталевої кулі. Навіть сама система не знає, яким навантаженням вона буде в будь-який момент у майбутньому.

    Зрештою, це дійсно не має значення

    Метою індикатора прогресу є, що це свідчить про те, що справді досягнуто прогресу, і відповідний процес не вивішений. Приємно, коли індикатор прогресу є точним, але зазвичай це лише незначне роздратування, коли це не так. Здебільшого, розробники не збираються приділяти багато часу і зусиль для алгоритмів роботи панелі прогресу, тому що, чесно кажучи, є набагато важливіші завдання, щоб витрачати час на.

    Звичайно, ви маєте повне право бути роздратованим, коли прогрес бар переходить до 99% завершено миттєво, а потім змушує вас чекати 5 хвилин для решти одного відсотка. Але якщо відповідна програма працює в цілому, просто нагадайте, що розробник мав свої пріоритети прямо.