Bash:我如何截断数组?

时间:2009-12-01 07:44:54

标签: linux arrays bash

我想更改数组的值,并希望得到任何帮助。

我有一个像这样的数组:

users=(root isometric akau)

(这实际上是当前用户的列表)我希望能够测试用户是否存在以及他们是否存在,然后从数组中删除该人。我已经尝试过将其放入for循环并进行评估:

for i in ${users[@]}; do
  eval "users=($([ -z $(grep \"^\$i\" /etc/shadow) ] && sed \"s/\$i//g\"))"
done

echo $users

我想过再玩这个,但我想我可能会变得太复杂(我不确定我可以把命令放在一个数组中)。任何人都知道如何做到这一点?

编辑:

我如何输入数组变量未设置数字:

cnt=0
for i in ${users[@]}; do
  [ -z "$(grep "^$i" /etc/shadow)" ] && unset users[cnt] || ((cnt++))
done

EDIT2:

实际上丹尼斯的表现更好。

4 个答案:

答案 0 :(得分:5)

您可能不需要for循环。试试这个:

users=(root isometric akau)
list="${users[@]/%/|}"      # convert array to list, add pipe char after each user
# strip the spaces from the list and look for usernames between the beg. of the line
# and the end of the word, make an array out of the result
users=($(grep -Eo "^(${list// })\>" /etc/shadow))

解开的grep看起来像这样:

grep -Eo "^(root|isometric|akau|)\>" /etc/shadow

答案 1 :(得分:4)

所以,如果你有......

$ users=(root isometric akau)
$ echo ${users[*]}
root isometric akau

您需要做的就是:

$ unset users[1]

然后......

$ echo ${users[*]}
root akau
$ 

答案 2 :(得分:0)

如果您要从jane移除users

users=(john joe mary jane liz root foobar)

for ((i = 0; i < ${#users[@]}; ++i)); do
    [[ ${users[i]} == jane ]] && break
done

users=(${users[@]:0:i} ${users[@]:i+1})

echo "${users[@]}" #=> john joe mary liz root foobar

一般原则是bash中没有数组切片(显然);你必须重新创建没有排除元素的数组。

也就是说,有许多方法可以在for(in)循环中完成你正在寻找的东西。

答案 3 :(得分:0)

users=(root nobody akau)
declare -a shadowusers
declare -a notinshadow
i=0
while IFS=":" read -r user b c d e f g h
do
    shadowusers[$i]=$user
    i=$((i+1))
done < "/etc/shadow"
for u in ${users[@]}
do
    found=0
    for s in ${shadowusers[@]}
    do
           case "$u" in
               "$s") found=1;;
           esac   
    done
    [ "$found" -eq 0 ] && notinshadow[$j]=$u
    j=$((j+1)) 
done 
echo ${notinshadow[@]}
相关问题