解剖这code,解释 - 检查是否另一个数组的数组子集 [英] dissecting this code, explanation - check if array subset of another array
问题描述
我发现这个例子在 wiki.bash-hackers.org
,但它不解释
细节,所以我在这里希望也许有人,可以把这个一些启示,并解释
发生了什么。
我理解 isSubset
函数的第一行,因为它正在通过指定参数时,使用间接
引用,商店钥匙进入内部数组 xkeys
和 ykeys
。
第2线路设置参数,但我不明白什么 $ {@ /%/ [关键]}
是干什么的?
貌似替代,改变%
到 [重点]
,我不知道这里发生了什么。
如果是,下一行它上的元素的数量相比较的阵列,但不应该它是反向,
返回1,如果一个数组有更多的元素,因为那时它不能被第二个子集?
最后 [[$ {2 + _!}&放大器;&安培; $ {!1} == $ {!2}]] ||返回1
,为pretty混乱。
isSubset(){
当地-a'xkeys =($ {!'$ 1'[@]})''ykeys =($ {!'$ 2'[@]})'
设置 - $ {@ /%/ [关键]} (($ {#xkeys [@]}< = $ {#ykeys [@]}))||返回1 本地密钥
在$ {xkeys [@]}键;做
[[$ {2 + _!}&放大器;&安培; $ {!1} == $ {!2}]] ||返回1
DONE
}主(){
#一为b的一个子集
当地-a'一=({} 0..5)''B =({0..10})
isSubset A B
回声$? #真 #一个包含一个键不在b的
本地-a'一个=([5] = 5 {6..11})''B =({0..10})'
isSubset A B
回声$? #假 #一个中包含的元素,其值!=B的相应构件
本地-a'一个=([5] = 5 6 8 9 10)''B =({0..10})'
isSubset A B
回声$? #假
}主要
2号线:
$ {@ /%/ [关键]}
%
作为模式的第一个字符表明图案具有匹配底。有没有在其他花纹所以意思是在年底更换空字符串,用'[关键]'。之后,位置参数是这样的:
1 = A [关键]
2 = B [关键]
下一行:
但它不应该是相反的,返回1,如果一个数组有更多的元素,
块引用>但做到这一点。请注意,
||
运算符使用,所以它将返回1
如果条件的不满足。条件是:x.size< = y.size,所以它会返回1
如果x.size> y.size最后:
[[$ {2 + _!}&放大器;&安培; $ {!1} == $ {!2}]] ||返回1
说实话,我不知道是什么
+ _
是。至于其他的,请注意,我们是在用键
变量循环。我们也有我们的位置的变量键
,所以:$ {!1}
变为
$ {A [关键])
和
键
变量需要从阵列A
键的值。所以整个测试验证,在给定的键值第二阵列中存在:[[$ {2 + _!}&放大器;&安培; ...
和与第一阵列在该密钥值是相同的,与所述第二阵列中的该密钥的值:
...&功放;&安培; $ {!1} == $ {!2}]
第一个条件是需要检测的情况下,当你通过数组
A
这在指数I
有空字符串和阵列b
不具有指数I
:本地-a'A =([1] =2 3)'B =([2] = {2} 3..10)
isSubset A B
回声$? #假I found this example at
wiki.bash-hackers.org
, however it is not explained in detail, so I was hoping maybe someone here, could put some light on this, and explain what is happening.I understand the first line of
isSubset
function, as it is taking passed args, and using indirect referencing, stores keys into internal arraysxkeys
andykeys
.2nd line is setting parameters, but I don't understand what
${@/%/[key]}
is doing? Looks like substitution, changing%
to[key]
, I have no clue what happens here.Then in next line it compares arrays on number of elements, but shouldn't it be reverse, returning 1 if first array has more elements, because then it can't be subset of the second one?
Finally
[[ ${!2+_} && ${!1} == ${!2} ]] || return 1
, is pretty confusing.isSubset() { local -a 'xkeys=("${!'"$1"'[@]}")' 'ykeys=("${!'"$2"'[@]}")' set -- "${@/%/[key]}" (( ${#xkeys[@]} <= ${#ykeys[@]} )) || return 1 local key for key in "${xkeys[@]}"; do [[ ${!2+_} && ${!1} == ${!2} ]] || return 1 done } main() { # "a" is a subset of "b" local -a 'a=({0..5})' 'b=({0..10})' isSubset a b echo $? # true # "a" contains a key not in "b" local -a 'a=([5]=5 {6..11})' 'b=({0..10})' isSubset a b echo $? # false # "a" contains an element whose value != the corresponding member of "b" local -a 'a=([5]=5 6 8 9 10)' 'b=({0..10})' isSubset a b echo $? # false } main
解决方案2nd line:
${@/%/[key]}
%
as first character of the pattern indicates that pattern has to match at the end. There is nothing else in the pattern so the meaning is "replace empty string at the end, with '[key]'". After that positional parameters look like this:1 = a[key] 2 = b[key]
Next line:
but shouldn't it be reverse, returning 1 if first array has more elements,
But it does that. Notice that
||
operator is used, so it will return1
if the condition is not met. The condition is: "x.size <= y.size", so it will return1
if "x.size > y.size".Finally:
[[ ${!2+_} && ${!1} == ${!2} ]] || return 1
To be honest, I don't know what
+_
is for. As for the rest, notice that we are in a loop with akey
variable. We also havekey
in our positional variables, so:${!1}
becomes
${a[key])
and
key
variable takes values of keys from arraya
. So the whole test verifies that value with given key exists in the second array:[[ ${!2+_} && ...
and that value with that key in the first array is the same as the value with that key in the second array:
... && ${!1} == ${!2} ]]
The first condition is necessary to detect the case when you pass array
a
which at indexi
has empty string and arrayb
which doesn't have indexi
:local -a 'a=([1]="" 2 3)' 'b=([2]=2 {3..10})' isSubset a b echo $? # false
这篇关于解剖这code,解释 - 检查是否另一个数组的数组子集的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!