Я бы оставил комментарии, но есть так много вещей, которые не так с этим.Простите, если это звучит грубо;это достаточно распространенное заблуждение, что я хочу быть кратким и точным, а не вежливым.
В качестве основного исправления терминологии здесь нет потоков.Существует две разные модели параллелизма, и Bash поддерживает только одну из них, а именно многопроцессорность. Потоки выполняются внутри одного процесса;но в Bash нет никакого способа управлять внутренними компонентами других процессов (и это в любом случае было бы довольно проблематично).Bash может запускать и останавливать процессы (не потоки) и делает это очень хорошо.
Но добавление параллелизма ЦП в попытке ускорить выполнение задач, не связанных с ЦП, является совершенно ошибочной идеей,Причина, по которой ввод-вывод занимает много времени, заключается в том, что ваш диск работает медленно.Ваш процессор простаивает большую часть времени, пока вращающийся диск (или даже твердотельный накопитель) заполняет и освобождает буферы DMA со скоростями, которые являются ледниковыми с точки зрения процессора.
Фактически, добавляя больше процессов, чтобы конкурировать заограниченная пропускная способность ввода-вывода может сделать медленнее, не быстрее;потому что канал ввода / вывода будет направлен на попытку сделать много вещей одновременно, где поддержание локальности было бы лучше (не перемещайте головку диска между несвязанными файлами, потому что вам придется вернуться назад на несколько миллисекунд, или аналогичнодля твердотельных накопителей, хотя и с гораздо менее важными эффектами, потоковая передача непрерывной области памяти будет более эффективной, чем рассеянный произвольный доступ.
В добавление к этому ваше повторное внедрение с ошибкой cat
будет ужасно медленным,Bash - это печально известный за то, что он очень неэффективен в while read
циклах.(Основной ошибкой является цитирование , но есть угловые случаи с read
, которых вы тоже хотите избежать.)
Кроме того, вы открываете файл,поиск в конце файла для добавления и закрытие его снова каждый раз в цикле.Вы можете избежать этого, переместив перенаправление за пределы цикла;
while IFS= read -r line || [[ -n $line ]]; do
printf '%s\n' "$line"
done >>final.txt
Но это все еще страдает от мучительной медлительности while read
.Если вы действительно хотите объединить эти файлы, я бы просто cat
их все последовательно.
cat A.TXT B.TXT C.TXT >final.txt
Если производительность ввода-вывода действительно вызывает озабоченность, объединение многих текстовых файлов в один текстовый файл, вероятно,шаг в неправильном направлении, хотя.Для получения информации, которую необходимо прочитать несколько раз, считывание ее в базу данных является распространенным способом ее ускорения.Инициализация и индексация базы данных добавляет некоторые накладные расходы заранее, но это быстро окупается, когда вы можете перебирать поля и записи гораздо быстрее и удобнее, чем когда они есть в последовательном файле.