我知道读取.csv文件只需使用此循环在bash中完成:
#!/bin/bash
INPUT=data.cvs
OLDIFS=$IFS
IFS=,
[ ! -f $INPUT ] && { echo "$INPUT file not found"; exit 99; }
while read flname dob ssn tel status
do
echo "Name : $flname"
echo "DOB : $dob"
echo "SSN : $ssn"
echo "Telephone : $tel"
echo "Status : $status"
done < $INPUT
IFS=$OLDIFS
但是我想稍微修改一下 - 我想让程序员在bash文件中定义列。 例如:
declare -a columns=("Name", "Surname", "ID", "Gender")
while read columns
do
//now echo everything that has been read
done < $INPUT
所以我想指定应该用作读取带有数组的CSV数据的容器的变量列表,然后在while体内访问该数组。
有办法吗?
答案 0 :(得分:1)
此解决方案的关键是下面while
声明之前的评论。 read
是内置的,但它仍然是一个命令,并且在执行命令之前shell会扩展命令参数。扩展${columns[@]}
后,命令变为
read Name Surname ID Gender
示例:
# Don't use commas in between array values (since they become part of the value)
# Values not quoted because valid names don't need quotes, and these
# value must be valid names
declare -a columns=(Name Surname ID Gender)
然后,我们可以尝试:
# Read is a command. Arguments are expanded.
# The quotes are unnecessary but it's hard to break habits :)
while read "${columns[@]}"; do
echo Name is "$Name"
# etc
done <<< "John Doe 27 M"
输出:
Name is John
即使在没有数组的shell中,这种方法也可以工作;列名可以只是一个空格分隔列表。 (示例在破折号,Posix shell中运行)
$ columns="Name Surname ID Gender"
$ # Here it is vital that $columns not be quoted; we rely on word-splitting
$ while read $columns; do
> echo Name is $Name
> done
John Doe 27 M
Name is John
...
答案 1 :(得分:0)
将该行读入数组,然后遍历该数组并创建一个使用列名的关联数组。
while read -r line
do
vals=($line)
declare -A colmap
i=0
for col in ${columns[@]}
do
colmap[col]=${vals[$i]}
let i=i+1
done
# do stuff with colmap here
# ...
unset colmap # Clear colmap before next iteration
done < $INPUT