Логотип Зефирнет

Ваша ментальная модель конвейеров Bash неверна?

Дата:

[Майкл Линч] столкнулся со странной ситуацией. Почему его программа компилировалась, а затем запускалась почти в 10 раз быстрее? быстрее чем просто запустить программу отдельно? [Майкл] столкнулся с этой проблемой во время сравнительного анализа проекта программирования, свел его к основам повторяемости и анализа и обнаружил, что это подчеркивает неверную ментальную модель того, как работают конвейеры bash.

Вот ситуация. Первое, что делает урезанная программа [Майкла], — это запускает таймер. Затем он просто читает и считает несколько байт из stdin, затем выводит, сколько времени потребовалось, чтобы это произошло. При запуске тестовой программы следующим образом это занимает около 13 микросекунд.

$ echo '00010203040506070809' | xxd -r -p | zig build run -Doptimize=ReleaseFast
bytes: 10
execution time: 13.549µs

При непосредственном запуске (уже скомпилированной) программы время выполнения увеличивается до 162 микросекунд.

$ echo '00010203040506070809' | xxd -r -p | ./zig-out/bin/count-bytes
bytes: 10
execution time: 162.195µs

Опять же, единственная разница между zig build run и ./zig-out/bin/count-bytes заключается в том, что сначала компилируется код, а потом сразу его выполняется. Второй просто запускает скомпилированную программу.

Как добавить дополнительный шаг компиляции снижение время выполнения? Оказывается, мысленная модель [Майкла] о том, как работают конвейеры bash, была неверной, и он отлично справляется с этой задачей. объясняя, как они на самом деле работают и почему это вызвало странное поведение он видел.

Короче говоря, команды в конвейере bash не запускаются последовательно. Все они запускаются одновременно и выполняются параллельно. Это означало, что при прямом запуске программа счетчика байтов [Майкла] запускалась немедленно. Затем он ждал около 150 микросекунд, ничего не делая, пока echo '00010203040506070809' | xxd -r -p часть конвейера приступила к доставке данных для чтения программой. Вот откуда возникает дополнительное время выполнения при запуске уже скомпилированной версии.

Так почему же его первая компиляция выполняется быстрее? Та же основная причина: когда zig build run команда запускается, сначала она тратит некоторое время на компиляцию программы. Затем, когда скомпилированная программа фактически запускается (и начинает таймер выполнения), входные данные из конвейера bash уже готовы. Таким образом, только что скомпилированная программа выполняется за меньшее время, поскольку ей не приходится ждать, пока станут доступны данные из более раннего этапа конвейера.

Это интересный взгляд на то, как на самом деле работают конвейеры bash, и мы в восторге от деталей, которые [Майкл] вкладывает в все это путешествие и объяснения. Рано или поздно такие детали всплывают и заставляют некоторых поднимать брови, как у пользователя, обнаружившего неприятные крайние случаи, связанные с пробелами в командах ssh.

Spot_img

Последняя разведка

Spot_img