说我有文件foo.txt
"The" "quick brown" "fox" "jumps over" "the" "lazy dog."
我想将文件中的这些“字段”读入一个数组。但是,如果该字段有空格,我的尝试将失败
$ read -a bar < foo.txt
$ echo ${bar[0]}
"The"
$ echo ${bar[1]}
"quick
使用declare
代替eval
:
declare -a "bar=( $( < foo.txt ) )"
这会强制将文件中的所有内容视为分配的右侧。使用eval
,文件的内容可以解释为代码。例如,如果文件包含
Some text ); echo "you just erased all your files"; ( true
然后执行以下操作eval
:
bar=( Some text ); echo "you just erased all your files"; ( true )
文件中的括号平衡了在命令替换之外使用的括号,导致文件中它们之间的文本作为代码执行,而不是用于填充数组。
这有效
$ read < foo.txt
$ eval bar=($REPLY)
$ echo ${bar[0]}
The
$ echo ${bar[1]}
quick brown
您的解决方案失败了,因为 bash 通常使用空格来分隔输入字段IFS
(这也是您得到引号的原因)。
read
如果您准备要处理的文本,则可以使用 plain :
IFS='"'
read -a bar < <(sed 's/"\([^"]*\)" */\1"/g' foo.txt)
echo ${bar[1]}
quick brown
注意: sed 命令将文件转换为以下格式:The"quick brown"fox"jumps over"the"lazy dog."
. 我将"
其用作分隔符,因为单词中绝对没有使用它。
这是使用FPAT变量GNU awk
的一种方法:
IFS=$'\n'
array=($(awk 'BEGIN { FPAT = "([^ ]+)|(\"[^\"]+\")" } { for (i=1; i<=NF; i++) print $i }' file.txt))
echo "${array[1]}"
结果:
"quick brown"