我有一个包含子目录和文件的数组:
~$ array=(elem1/a elem1/b elem2/a elem2/b)
我需要在子目录 elem1 中选择所有文件(及其子目录)。
我已尝试使用 for 循环和案例:
for element in "${array[@]}"; do
case $element in
elem1*)
# action I need to perform on this element
echo "This is $element"
;;
esac
done
我希望使用一些glob来获取我需要的元素列表,方法与此类似(从数组元素中减去子字符串):
~$ echo ${array[@]%/a}
elem1 elem1/b elem2 elem2/b
我主要担心的是,我不会硬编码我要搜索的字符串,因为我不知道它的内容 - 在我的最终版本中我得到了它们来自另一个阵列。
答案 0 :(得分:2)
我的答案会在不同的行中打印数组的每个元素,然后过滤您感兴趣的元素(grep
)并将它们放入新数组
newarray=( $(printf "%s\n" "${array[@]}" | grep ^elem/) )
唯一的问题是,如果数组(subdirs和file namews)的元素可能包含 EOL 或空白字符。
<强>加成强>
如果您的元素包含 EOL 或空白字符,则应使用 NUL (\000
)字符和grep -zZ
来处理它;但是你需要更多的代码才能将那些NUL-char字符串变成bash可以使用的东西 - 当bash找到NUL字符时bash停止读取。
在这个例子中,我使用awk
来处理NUL字符没有问题,并且不必使用grep
:
eval newarray=( $(printf "%s\000" "${A[@]}" |
awk 'BEGIN { FS="\000" }
/^elem\// {
gsub("\042","\\\042")
printf("[" NR-1 "]=\042%s\042 ",$0)
}'
)
)
答案 1 :(得分:1)
这是另一种选择
$ for e in "${array[@]}";
do case "${e%%/*}" in
elem1) echo "$e is in elem1" ;;
esac
done
elem1/a is in elem1
elem1/b is in elem1
答案 2 :(得分:1)
您可以使用变量查询(下面为prefix
)过滤数组,并将结果存储在新数组(result
)中:
#!/bin/bash
array=(elem1/a elem1/b elem2/a elem2/b)
prefix=elem1
result=()
for element in "${array[@]}"; do
[[ $element == $prefix/* ]] && result+=("$element")
done
结果是:
$ declare -p result
declare -a result='([0]="elem1/a" [1]="elem1/b")'