我可以检查三元运算符中的退出代码吗?
Can I examine exit code within ternary operator?
我正在尝试根据 test
内置和三元运算符的退出代码打印一个字符串。我成功了:
b=5
echo $(( b==5 ? good : bad )) # good is printed
good 按预期打印,但如果我这样做:
echo $(( test $b -eq 50 ? 123 : 321 ))
test 5 -eq 50 ? 123 : 321 : syntax error in expression (error token is "5 -eq 50 ? 123 : 321 ")
echo $(( $(test $b -eq 5)==0 ? 123 : 321 ))
==0 ? 123 : 321 : syntax error: operand expected (error token is "==0 ? 123 : 321 ")
假设我想报告文件存在,以下 none 也不起作用:
echo $(( $((test -e file))==0 ? 123 : 321 ))
test -e file: syntax error in expression (error token is "file")
echo $(( ((test -e file))==0 ? 123 : 321 ))
((test -e file))==0 ? 123 : 321 : missing `)' (error token is "file))==0 ? 123 : 321 ")
echo $(( (test -e file)==0 ? 123 : 321 ))
(test -e file)==0 ? 123 : 321 : missing `)' (error token is "file)==0 ? 123 : 321 ")
echo $(( "test -e file" ? 123 : 321 ))
"test -e file" ? 123 : 321 : syntax error: operand expected (error token is ""test -e file" ? 123 : 321 ")
三元运算符中是否有任何可能的构造可以检查退出代码?
$(( arithmetic context ))
需要一个算术表达式;显然随机字符串(显然你希望作为命令执行)不是算术表达式,所以这是一个语法错误。
大概试试
echo $(( $(test "$b" -eq 50; echo $?) ? 123 : 321 ))
等;但显然,一种更简单、更地道的说法是
test "$b" -eq 50 && echo 123 || echo 321
你无法重构 echo
;在这个孤立的例子中,这只是一个小小的不便。如果您确实需要避免重复更复杂的代码,请将 echo
替换为封装您不想重复的任何内容的函数。
A $(command substitution)
将命令替换为打印到标准输出的任何内容。如果你想检查它的退出代码,你需要它把它(而不是别的)打印到标准输出,或者使用不同的结构。
或者,使用数组索引。
典型构造:
b=5
str=(bad good)
echo "${str[b==5]}"
这使用算术比较的输出作为数组索引。
字符串作为消息
您可以将消息数组构建为:
MSGS=('Good result' 'Wrong result' [123]='Existing entry' [321]='Broken link')
然后你需要一些常数:
good=0 bad=1 exist=123 notexist=321
然后使用整数作为:
b=5 file=/tmp
printf "B: %s %s, Entry: '%s' %s\n" "$b" "${MSGS[ b==5 ? good : bad ]}" \
"$file" "${MSGS[ $(test -e "$file";echo $?) ? notexist : exist ]}"
B: 5 Good result, Entry: '/tmp' Existing entry
或
b=12 file=/tnt
printf "B: %s %s, Entry: '%s' %s\n" "$b" "${MSGS[ b==5 ? good : bad ]}" \
"$file" "${MSGS[ $(test -e "$file";echo $?) ? 321 : 123 ]}"
B: 12 Wrong result, Entry: '/tnt' Broken link
快游戏示例:
简单使用消息数组选择数字游戏。
GAMMSGS=(Exact 'Too small' 'Too big') target=$((RANDOM%10)) ANSWER=''
while [ "$ANSWER" != "Exact" ]; do
read -n 1 -p 'Enter a digit: ' play
ANSWER=${GAMMSGS[ target == play ? 0 : target > play ? 1 : 2 ]}
echo -e \nYou try $play: $ANSWER
done
样本运行:
Enter a digit: 0
You try 0: Too small
Enter a digit: 9
You try 9: Too big
Enter a digit: 5
You try 5: Too big
Enter a digit: 3
You try 3: Exact
我正在尝试根据 test
内置和三元运算符的退出代码打印一个字符串。我成功了:
b=5
echo $(( b==5 ? good : bad )) # good is printed
good 按预期打印,但如果我这样做:
echo $(( test $b -eq 50 ? 123 : 321 ))
test 5 -eq 50 ? 123 : 321 : syntax error in expression (error token is "5 -eq 50 ? 123 : 321 ")
echo $(( $(test $b -eq 5)==0 ? 123 : 321 ))
==0 ? 123 : 321 : syntax error: operand expected (error token is "==0 ? 123 : 321 ")
假设我想报告文件存在,以下 none 也不起作用:
echo $(( $((test -e file))==0 ? 123 : 321 ))
test -e file: syntax error in expression (error token is "file")
echo $(( ((test -e file))==0 ? 123 : 321 ))
((test -e file))==0 ? 123 : 321 : missing `)' (error token is "file))==0 ? 123 : 321 ")
echo $(( (test -e file)==0 ? 123 : 321 ))
(test -e file)==0 ? 123 : 321 : missing `)' (error token is "file)==0 ? 123 : 321 ")
echo $(( "test -e file" ? 123 : 321 ))
"test -e file" ? 123 : 321 : syntax error: operand expected (error token is ""test -e file" ? 123 : 321 ")
三元运算符中是否有任何可能的构造可以检查退出代码?
$(( arithmetic context ))
需要一个算术表达式;显然随机字符串(显然你希望作为命令执行)不是算术表达式,所以这是一个语法错误。
大概试试
echo $(( $(test "$b" -eq 50; echo $?) ? 123 : 321 ))
等;但显然,一种更简单、更地道的说法是
test "$b" -eq 50 && echo 123 || echo 321
你无法重构 echo
;在这个孤立的例子中,这只是一个小小的不便。如果您确实需要避免重复更复杂的代码,请将 echo
替换为封装您不想重复的任何内容的函数。
A $(command substitution)
将命令替换为打印到标准输出的任何内容。如果你想检查它的退出代码,你需要它把它(而不是别的)打印到标准输出,或者使用不同的结构。
或者,使用数组索引。
典型构造:
b=5
str=(bad good)
echo "${str[b==5]}"
这使用算术比较的输出作为数组索引。
字符串作为消息
您可以将消息数组构建为:
MSGS=('Good result' 'Wrong result' [123]='Existing entry' [321]='Broken link')
然后你需要一些常数:
good=0 bad=1 exist=123 notexist=321
然后使用整数作为:
b=5 file=/tmp
printf "B: %s %s, Entry: '%s' %s\n" "$b" "${MSGS[ b==5 ? good : bad ]}" \
"$file" "${MSGS[ $(test -e "$file";echo $?) ? notexist : exist ]}"
B: 5 Good result, Entry: '/tmp' Existing entry
或
b=12 file=/tnt
printf "B: %s %s, Entry: '%s' %s\n" "$b" "${MSGS[ b==5 ? good : bad ]}" \
"$file" "${MSGS[ $(test -e "$file";echo $?) ? 321 : 123 ]}"
B: 12 Wrong result, Entry: '/tnt' Broken link
快游戏示例:
简单使用消息数组选择数字游戏。
GAMMSGS=(Exact 'Too small' 'Too big') target=$((RANDOM%10)) ANSWER=''
while [ "$ANSWER" != "Exact" ]; do
read -n 1 -p 'Enter a digit: ' play
ANSWER=${GAMMSGS[ target == play ? 0 : target > play ? 1 : 2 ]}
echo -e \nYou try $play: $ANSWER
done
样本运行:
Enter a digit: 0
You try 0: Too small
Enter a digit: 9
You try 9: Too big
Enter a digit: 5
You try 5: Too big
Enter a digit: 3
You try 3: Exact