На работе я часто пишу сценарии bash. Мой руководитель предложил разбить весь сценарий на функции, как показано в следующем примере:
#!/bin/bash
# Configure variables
declare_variables() {
noun=geese
count=three
}
# Announce something
i_am_foo() {
echo "I am foo"
sleep 0.5
echo "hear me roar!"
}
# Tell a joke
walk_into_bar() {
echo "So these ${count} ${noun} walk into a bar..."
}
# Emulate a pendulum clock for a bit
do_baz() {
for i in {1..6}; do
expr $i % 2 >/dev/null && echo "tick" || echo "tock"
sleep 1
done
}
# Establish run order
main() {
declare_variables
i_am_foo
walk_into_bar
do_baz
}
main
Есть ли какая-либо причина, чтобы сделать это, кроме «читабельности», которая, я думаю, могла бы быть одинаково хорошо обоснована еще несколькими комментариями и небольшим межстрочным интервалом?
Делает ли это сценарий более эффективным (я бы ожидал обратного, если что-нибудь), или это облегчает изменение кода за пределами вышеупомянутого потенциала читабельности? Или это действительно просто стилистическое предпочтение?
Обратите внимание, что, хотя сценарий демонстрирует это не очень хорошо, «порядок выполнения» функций в наших реальных сценариях имеет тенденцию быть очень линейным - walk_into_bar
зависит от того, что i_am_foo
сделано, и do_baz
действует от материала, установленного walk_into_bar
- так что возможность произвольно поменять порядок выполнения - это не то, что мы обычно делаем. Например, вы бы не захотели вдруг поставить declare_variables
после walk_into_bar
, что сломало бы вещи.
Пример того, как я написал бы вышеупомянутый сценарий, был бы:
#!/bin/bash
# Configure variables
noun=geese
count=three
# Announce something
echo "I am foo"
sleep 0.5
echo "hear me roar!"
# Tell a joke
echo "So these ${count} ${noun} walk into a bar..."
# Emulate a pendulum clock for a bit
for i in {1..6}; do
expr $i % 2 >/dev/null && echo "tick" || echo "tock"
sleep 1
done
local
- это обеспечивает переменную область действия, которая невероятно важна в любом нетривиальном скрипте.
main()
вверху и добавляюmain "$@"
внизу, чтобы вызвать его. Это позволяет вам сразу увидеть высокоуровневую логику скрипта при ее открытии.