我想编写一个bash函数来检查文件是否具有某些属性并返回true或false。然后我可以在我的脚本中使用它“if”。但是我该怎么回事呢?
function myfun(){ ... return 0; else return 1; fi;}
然后我像这样使用它:
if myfun filename.txt; then ...
当然这不起作用。如何实现这一目标?
答案 0 :(得分:281)
使用0表示true,使用1表示false。
样品:
#!/bin/bash
isdirectory() {
if [ -d "$1" ]
then
# 0 = true
return 0
else
# 1 = false
return 1
fi
}
if isdirectory $1; then echo "is directory"; else echo "nopes"; fi
修改强>
来自@ amichair的评论,这些也是可能的
isdirectory() {
if [ -d "$1" ]
then
true
else
false
fi
}
isdirectory() {
[ -d "$1" ]
}
答案 1 :(得分:110)
不是0 = true
和1 = false
。它是:零表示没有失败(成功) ,非零表示失败(类型N) 。
虽然selected answer在技术上是“真实的”但,请不要在您的代码中添加return 1
** false 。它会有几个不幸的副作用。
bash manual说(强调我的)
return [n]
导致shell函数停止执行并将值n返回给其调用者。 如果未提供n ,则返回值为函数中最后执行的命令的退出状态。
因此,我们不必使用0和1来表示True和False。他们这样做的事实本质上是微不足道的知识,仅用于调试代码,面试问题和吹响新手的思想。
bash手册also says
否则函数的返回状态是执行的最后一个命令的退出状态
bash手册also says
哇,等等。管道?让turn to the bash manual再一次。( $?)扩展到最近执行的前台管道的退出状态。
管道是一个或多个命令的序列,由一个控制运算符'|'或'|&'分隔。
是。他们说1命令是一个管道。因此,所有这三个引用都在说同样的事情。
$?
告诉你最后发生了什么。所以,虽然@Kambus demonstrated具有如此简单的功能,但根本不需要return
。我认为
与大多数阅读此内容的人的需求相比,这是不切实际的简单。
return
?如果函数要返回其最后一个命令的退出状态,为什么要使用return
?因为它会导致函数停止执行。
01 function i_should(){
02 uname="$(uname -a)"
03
04 [[ "$uname" =~ Darwin ]] && return
05
06 if [[ "$uname" =~ Ubuntu ]]; then
07 release="$(lsb_release -a)"
08 [[ "$release" =~ LTS ]]
09 return
10 fi
11
12 false
13 }
14
15 function do_it(){
16 echo "Hello, old friend."
17 }
18
19 if i_should; then
20 do_it
21 fi
行04
是一个显式的[-ish]返回true,因为&&
的RHS只有在LHS为真时才会被执行
行09
返回与行08
由于行13
12
返回false
(是的,这可以打高尔夫,但整个例子都是人为的。)
# Instead of doing this...
some_command
if [[ $? -eq 1 ]]; then
echo "some_command failed"
fi
# Do this...
some_command
status=$?
if ! $(exit $status); then
echo "some_command failed"
fi
请注意设置status
变量如何揭开$?
的含义。 (当然你知道$?
意味着什么,但是那些知识不足你的人有一天会把它当作谷歌。除非你的代码进行高频交易,show some love,设置变量。)但真实的外卖是“如果不存在状态”或相反“如果退出状态”可以大声朗读并解释其含义。 但是,最后一个可能有点过于雄心勃勃,因为看到单词exit
可能会让你认为它正在退出脚本,而实际上它正在退出$(...)
子shell
**如果您绝对坚持使用return 1
为假,我建议您至少使用return 255
。这将导致您未来的自我,或任何其他必须维护您的代码的开发人员质疑“为什么是255?”然后他们至少会注意并有更好的机会避免错误。
答案 2 :(得分:30)
myfun(){
[ -d "$1" ]
}
if myfun "path"; then
echo yes
fi
# or
myfun "path" && echo yes
答案 3 :(得分:13)
使用选项-d!时检查目录时要小心 如果变量$ 1为空,则检查仍将成功。当然,还要检查变量是否为空。
#! /bin/bash
is_directory(){
if [[ -d $1 ]] && [[ -n $1 ]] ; then
return 0
else
return 1
fi
}
#Test
if is_directory $1 ; then
echo "Directory exist"
else
echo "Directory does not exist!"
fi
答案 4 :(得分:4)
出于代码可读性的原因,我相信返回true / false应该:
return
,后跟另一个关键字(true
或false
)我的解决方案是return $(true)
或return $(false)
,如下所示:
is_directory()
{
if [ -d "${1}" ]; then
return $(true)
else
return $(false)
fi
}
答案 5 :(得分:2)
在true
之前紧接使用false
或return
命令,然后在不带参数的情况下使用return
。 return
将自动使用上一个命令的值。
为return
提供参数是不一致的,如果您未使用1或0,则类型特定并且容易出错。并且如先前的评论所述,此处使用1或0并不是实现此功能的正确方法
#!/bin/bash
function test_for_cat {
if [ $1 = "cat" ];
then
true
return
else
false
return
fi
}
for i in cat hat;
do
echo "${i}:"
if test_for_cat "${i}";
then
echo "- True"
else
echo "- False"
fi
done
输出:
$ bash bash_return.sh
cat:
- True
hat:
- False
答案 6 :(得分:1)
如果你改写它可能会有用
function myfun(){ ... return 0; else return 1; fi;}
function myfun(){ ... return; else false; fi;}
。也就是说,如果false
是函数中的最后一条指令,则会得到整个函数的错误结果,但无论如何return
中断函数的结果都是真实的。我相信至少对我的bash口译员来说这是真的。
答案 7 :(得分:1)
我发现测试函数输出的最短形式就是
do_something() {
[[ -e $1 ]] # e.g. test file exists
}
do_something "myfile.txt" || { echo "File doesn't exist!"; exit 1; }
答案 8 :(得分:0)
我遇到了一个绊脚石(尚未明确提及?)。也就是说,不是如何返回布尔值,而是如何正确地对其进行求值!
我试图说if [ myfunc ]; then ...
,但这完全是错误的。请勿使用括号! if myfunc; then ...
是做到这一点的方法。
与@Bruno和其他人重申的一样,true
和false
是命令,而不是值!这对于理解shell脚本中的布尔值非常重要。
在这篇文章中,我使用布尔值变量:https://stackoverflow.com/a/55174008/3220983进行了解释和演示。我强烈建议您检查一下,因为它是如此紧密相关。
在这里,我将提供一些从函数返回和评估布尔值的示例:
此:
test(){ false; }
if test; then echo "it is"; fi
不产生回声输出。 (即false
返回否)
test(){ true; }
if test; then echo "it is"; fi
产生:
it is
(即true
返回 true)
和
test(){ x=1; }
if test; then echo "it is"; fi
产生:
it is
因为隐式返回了0(即true)。
现在,这就是把我搞砸了...
test(){ true; }
if [ test ]; then echo "it is"; fi
产生:
it is
AND
test(){ false; }
if [ test ]; then echo "it is"; fi
ALSO产生:
it is
使用此处的括号会产生误报! (我推断“外部”命令的结果为0。)
我文章的主要收获是:不要像使用典型的相等性检查那样使用方括号来评估布尔函数(或变量)。 if [ x -eq 1 ]; then...
!
答案 9 :(得分:0)
紧接着@Bruno Bronosky和@mrteatime,我建议您只将布尔返回值写为“ backwards”。这就是我的意思:
foo()
{
if [ "$1" == "bar" ]; then
true; return
else
false; return
fi;
}
这消除了每个return语句的难看的两行要求。