我有一个脚本,我需要在其中对字符串变量的内容进行所有可能的比较。每种组合都需要对变量内容采用不同的方法,因此如下所示:
if $a contains "a" AND "b" AND "c"; then do x
elif $a contains "a" AND "b" but NOT "c"; then do y
elif $a contains "b" AND "c" but NOT "a"; then do z
...
据我所知,这样做的方法是构造一个像这样的 if 条件:
if [[ $A == *"b"* ]] && [[ $A == *"c"* ]] && [[ $A == *"d"* ]]
elif [[ $A == *"b"* ]] && [[ $A == *"c"* ]]
elif [[ $A == *"c"* ]] && [[ $A == *"d"* ]]
elif [[ $A == *"b"* ]] && [[ $A == *"d"* ]]
elif [[ $A == *"b"* ]]
elif [[ $A == *"c"* ]]
elif [[ $A == *"d"* ]]
fi
但这当然太复杂了,因为我的变量($A)和子字符串(b,c,d)的名称比这长得多。所以我想看看是否有办法将条件表达式的内容保存到变量中:
contains_b= *a condition for [[ $A == *"b"* ]]*; echo $contains_b
-> 真 | 错误的
我只在这里找到了回复[ contains_b=$(! [ "$A" = *"b"* ]; echo $?)
]; 但是,$contains_b -> 0
在随后的条件句中不起作用,因为:
if $contains_b; then do x; fi
->bash: [0]: command not found
所以我能想到的唯一解决方案是手动完成:
if [[ $A == *"b"* ]]; then
contains_b=true
else
contains_b=false
fi
但是,我最终会执行三个 if 语句来获取三个变量,以及每个不同组合的其他 7 个比较。
我想知道是否有不同/更有效的方法。如果没有,您对进行这些多重比较的另一种方法有什么建议吗?我觉得我把它弄得太复杂了......
感谢您的任何帮助。
创建一个二进制掩码,然后对其进行操作。这样做的好处是每个测试只执行一次,并将测试与对测试结果的操作分开。
请注意,代码将模式用作扩展的正则表达式。要将它们作为字符串进行比较,请使用
代替
在下面的代码中。
或者,使用带有 1 和 0 的字符串掩码(0 表示不匹配,1 表示匹配)。请注意,
mask
下面的字符串与上面代码中使用的数字的实际二进制表示相反。每个脚本的输出将是
...因为字符串
abba
匹配前两个模式,a
并且b
.这里使用
bash
4.0或更高版本或mksh
R40或更高版本,您可以通过两个case
语句完成所有操作:'s is的
zsh
等价物bash
;;&
;|
也受mksh
.一旦你得到一个数字的结果,你应该对它使用算术运算,而不是把它作为命令运行:
=~
可以通过在 bash 中使用正则表达式匹配测试每个可能的匹配模式一次来构建二进制数。为了以正确的顺序构建二进制数(MSB 保留并对应于最后执行的测试),我们需要将(否定的)退出代码添加到变量中。只是先前答案的替代解决方案。