linux – bash脚本和zsh shell中的数组行为(开始索引0或1?)

我需要阐述shell脚本中数组的以下行为:

想象一下,给出以下内容:

arber@host ~> ls
fileA fileB script.sh

现在我可以执行以下命令:

arber@host ~> ARR=($(ls -d file*))
arber@host ~> echo ${ARR[0]}          # start index 0

arber@host ~> echo ${ARR[1]}          # start index 1
fileA
arber@host ~> echo ${ARR[2]}          # start index 2
fileB

但是当我通过script.sh执行此操作时,它的行为会有所不同(Start Index = 0):

arber@host ~> cat script.sh
#!/bin/bash
ARR=($(ls -d file*))

# get length of an array
aLen=${#ARR[@]}

# use for loop read all items (START INDEX 0)
for (( i=0; i<${aLen}; i++ ));
do
  echo ${ARR[$i]}
done

结果如下:

arber@host ~> ./script.sh
fileA
fileB

我使用Ubuntu 18.04 LTS和zsh.有人可以解释一下吗?

解决方法:

Arrays in Bash are indexed from zeroin zsh they’re indexed from one.

但是你不需要像这样的简单用例的索引.循环遍及${array [@]}同时适用于:

files=(file*)
for f in "${files[@]}"; do
    echo "$f"
done

在zsh中你也可以使用$files而不是“${files [@]}”,但这在Bash中不起作用. (并且它会删除空数组元素,但是你不会从文件名中获取任何内容.)

另外,不要使用$(ls file *),如果你有带空格的文件名,它会中断(见WordSpliting on BashGuide),并且开始时完全没用.

shell完全能够自己生成文件名.那实际上会发生什么,shell找到名称与文件*匹配的所有文件,将它们传递给ls,然后再将它们打印出来供shell读取和处理.

相关文章

用的openwrt路由器,家里宽带申请了动态公网ip,为了方便把2...
#!/bin/bashcommand1&command2&wait从Shell脚本并行...
1.先查出MAMP下面集成的PHP版本cd/Applications/MAMP/bin/ph...
1、先输入locale-a,查看一下现在已安装的语言2、若不存在如...
BashPerlTclsyntaxdiff1.进制数表示Languagebinaryoctalhexa...
正常安装了k8s后,使用kubect工具后接的命令不能直接tab补全...