Привет. Я устал от сложностей написания Bash курса и решил отдохнуть и написать статью.
Сегодня поговорим об очень редко используемом и на мой взгляд, абсолютно ненужном и неадекватно работающем операторе bash. И сравним его с классикой.
Представляю Вашему вниманию тернарный (троичный) оператор.
В мануале он выглядит так:
expr1 ? expr2 : expr3
expr1 истина, то результат expr2, иначе expr3.Для исследования я написал небольшую тестовую программу
#!/bin/bash
declare -i c=033 #27
declare -i d=044 #36
declare -i k=0 #counter
function wait2sec(){
sleep 2
echo $1
}
SECONDS=0
a=$((1 == 2?$(wait2sec c):$(wait2sec d))) #0
echo $((k++)) sec=$SECONDS a=$a
SECONDS=0
((a=1==2?$(wait2sec c):$(wait2sec d))) #1
echo $((k++)) sec=$SECONDS a=$a
SECONDS=0
a=$((1==2?$(wait2sec c):$(wait2sec d))) #2
echo $((k++)) sec=$SECONDS a=$a
SECONDS=0
[[ 1 == 2 ]] && a=$(wait2sec c) || a=$(wait2sec d) #3
echo $((k++)) sec=$SECONDS a=$a
SECONDS=0
[[ 1==2 ]] && a=$(wait2sec c) || a=$(wait2sec d) #4
echo $((k++)) sec=$SECONDS a=$a
####### result #############
# 0 sec=4 a=36
# 1 sec=4 a=36
# 2 sec=4 a=36
# 3 sec=2 a=d
# 4 sec=2 a=c
Функция wait2sec ждет 2 секунды и печатает первый параметр. Дальше идут пять как бы одинаковых блоков.
1 == 2 - expr1 (false)
wait2sec c - expr2
wait2sec d - expr3
Анализируем результаты:
переменные
dи с описаны как целые, но начинаются с0, поэтому bash интерпретирует их как восьмеричные.Тернарный оператор может использоваться только внутри арифметической подсистемы
((…)), в которой переменные допускается извлекать(получать значение) без знака$, поэтомуcиdинтерпретируются как переменные.У тернарного оператора допустима даже “упоротая” форма (блок 1)
В математической подсистеме при сравнении пробелы вокруг знака сравнения не влияют на результат.
В блоке 4 допущена ошибка (нет пробелов вокруг знака сравнения, поэтому
1==2- интерпретируется не как результат сравнения, а как не пустая строка, поэтому результат (истина) неверный. Такие ошибки очень трудно отлаживать.В отличие от классического, башевского, сравнения при использовании тернарного оператора
expr2иexpr3вычисляются вне зависимости от условия. Об этом говорит удвоенное время выполнения блока.








Комментарии