Ответ 1
В большинстве случаев предпочтительнее нажать wget
в фоновом режиме с помощью &
или -b
, вы можете использовать xargs
для того же эффекта и лучше.
Преимущество состоит в том, что xargs
будет правильно синхронизироваться без дополнительной работы. Это означает, что вы можете безопасно получать доступ к загруженным файлам (при условии, что ошибка не возникает). Все загрузки будут завершены (или не удалены) после выхода xargs
, и по коду выхода вы знаете, все ли прошло хорошо. Это гораздо предпочтительнее ожидание с sleep
и тестирование для завершения вручную.
Предполагая, что URL_LIST
- это переменная, содержащая все URL-адреса (может быть построена с помощью цикла в примере OP, но также может быть списком, созданным вручную), запустив это:
echo $URL_LIST | xargs -n 1 -P 8 wget -q
будет передавать один аргумент за раз (-n 1
) до wget
и выполнять не более 8 параллельных процессов wget
за раз (-P 8
). xarg
возвращается после завершения последнего порожденного процесса, что мы хотели знать. Никаких дополнительных обманщиков не требуется.
"Магическое число" из 8 параллельных загрузок, которые я выбрал, не задано в камне, но это, вероятно, хороший компромисс. В "максимизации" серии загрузок есть два фактора:
Один заполняет "кабель", то есть использует доступную полосу пропускания. Предполагая, что "нормальные" условия (сервер имеет большую пропускную способность, чем клиент), это уже происходит с одной или двумя загрузками. Выбросы большего количества подключений при этой проблеме приведут только к удалению пакетов и управлению нагрузкой на TCP-загрузку, а N загружает с асимптотически шириной 1/N каждый к одному и тому же сетевому эффекту (минус упавшие пакеты, минус восстановление размера окна). Упавшие пакеты - это обычная вещь, которая должна произойти в сети IP, так как предполагается, что управление перегрузкой должно работать (даже с одним соединением), и обычно воздействие практически равно нулю. Однако наличие неоправданно большого числа соединений усиливает этот эффект, поэтому это может стать заметным. В любом случае, это не делает ничего быстрее.
Второй фактор - создание соединения и обработка запросов. Здесь действительно помогает несколько дополнительных соединений в полете. Одной из проблем является латентность двух круглых поездок (обычно 20-40 мс в одной и той же географической области, 200-300 мс между континентами) плюс нечетные 1-2 миллисекунды, которые серверу действительно нужно обработать запрос и нажать ответ к гнезду. Это не так много времени, но умножается на несколько сотен тысяч запросов, это быстро складывается.
Имея что-то от полудюжины до десятка запросов в полете, скрывает большую или всю эту задержку (она все еще там, но поскольку она перекрывается, она не суммируется!). В то же время наличие нескольких параллельных соединений не оказывает неблагоприятного воздействия, например, вызывает чрезмерную перегрузку или принуждает сервер к открытию новых процессов.