awk -F '|' '$1 ~ /smiths/ {sum += $3} END {print sum}' inputfilename
-F
устанавливает разделитель полей; Я заключил его в одинарные кавычки, потому что это специальный символ оболочки. $ 1 ~ / smiths /
применяет следующий {кодовый блок} только к строкам, первое поле которых соответствует регулярному выражению / smiths /
. Обратите внимание, что, поскольку вы на самом деле не используете здесь регулярное выражение, а только конкретное значение, вы можете так же легко использовать:
awk -F '|' '$1 == "smiths" {sum += $3} END {print sum}' inputfilename
Которая проверяет равенство строк. Это эквивалентно использованию регулярного выражения / ^ smiths $ /
, как упоминалось в другом ответе, который включает привязку ^
, чтобы соответствовать только началу строки (начало поля 1 ) и привязку $
, чтобы соответствовать только концу строки. Не уверен, насколько вы знакомы с регулярными выражениями. Они очень мощные, но в этом случае вы можете также легко использовать проверку равенства строк.
Я не уверен, насколько это чище, чем ваша существующая функция, но использование ассоциативного массива (требует bash версии 4.0 или более поздней )в сочетании с циклом for, который вы могли бы использовать для чтения один раз.
function prompt_user() {
declare -A prompt_questions
vars=(IMAGE_NAME IP_ADDRESS PORT_ONE PORT_TWO CONTAINER_NAME NODE_NAME HOST_DIRECTORY REMOTE_DIRECTORY)
prompt_questions=(
[IMAGE_NAME]='Image Name'
[IP_ADDRESS]='IP Address'
[PORT_ONE]='Port 1'
[PORT_TWO]='Port 2'
[CONTAINER_NAME]='Container Name'
[NODE_NAME]='Node Name'
[HOST_DIRECTORY]="Host Directory (Can leave this blank if you're building a new image)"
[REMOTE_DIRECTORY]="Remote Directory (Can leave this blank if you're building a new image)"
)
cat <<EOF
Enter details for docker build! If it's a new build, you can leave Host Directory and Remote Directory blank.
If you've already assigned variables and are running the host you can leave the already filled vars blank if you entered them before
Enter details:
EOF
for var in "${vars[@]}"; do
read -rp "${prompt_questions[$var]}: " "$var"
done
}
Я не думаю, что ваш текущий код так уж плох. Единственная повторяющаяся часть — read -p
, состоящая всего из пары символов. В любом случае, вы не можете избавиться от имен переменных или подсказок.
(Тем не менее, есть то, что кто-то может предпочесть аргументы строки команды -вместо сценариев, которые задают вопросы в интерактивном режиме, но это вопрос предпочтения.)
В любом случае, поскольку я сказал, что мне не особенно нравится двойной -список имен переменных @Jesse _b, который требуется ассоциативному массиву, вот еще одна альтернатива:
prompt_user() {
queries=(
IMAGE_NAME='Image Name'
IP_ADDRESS='IP Address'
PORT_ONE='Port 1'
PORT_TWO='Port 2'
CONTAINER_NAME='Container Name'
NODE_NAME='Node Name'
HOST_DIRECTORY="Host Directory (Can leave this blank if you're building a new image)"
REMOTE_DIRECTORY="Remote Directory (Can leave this blank if you're building a new image)"
)
echo "Enter details for docker build! If it's a new build, you can leave Host Directory and Remote Directory blank."
echo "If you've already assigned variables and are running the host you can leave the already filled vars blank if you entered them before"
echo " "
echo "Enter details:"
for query in "${queries[@]}"; do
read -rp "${query#*=}: " "${query%%=*}"
done
}
"${query#*=}"
и "${query%%=*}"
эффективно разбивают строку в query
по первому знаку равенства.