如何用Bash的readarray/while循环处理CSV格式文件内容?
处理逗号分隔文本的几种Shell脚本实现
假设待处理的输入/文件内容如下:
1,a,info 2,b,inf 3,c,in
方案1:完善版read while循环
你提供的示例可以补充分割数组的逻辑,用IFS指定分隔符,结合read -ra将行内容存入数组:
while read r ; do echo "当前行内容:$r" # 按','分割行内容到数组arr,-r避免转义反斜杠,-a指定数组名 IFS=',' read -ra arr <<< "$r" # 示例操作:输出第二个元素,对第三个元素做md5sum echo "第二个元素:${arr[1]}" echo "${arr[2]}" | md5sum done <<HEREDOC 1,a,info 2,b,inf 3,c,in HEREDOC
方案2:readarray(mapfile)结合循环实现
readarray是bash内置命令,mapfile是它的别名,作用是将输入的每一行读取到数组中,适合批量处理多行内容。
基础用法:直接读取静态内容到数组
把HEREDOC或文件内容直接读入数组,再用while循环遍历:
# -t 参数用于移除每行末尾的换行符,避免数组元素带换行 readarray -t lines <<HEREDOC 1,a,info 2,b,inf 3,c,in HEREDOC # 用while循环遍历数组(也可以用for循环) index=0 while [[ $index -lt ${#lines[@]} ]]; do line=${lines[$index]} echo "当前行内容:$line" # 同样按','分割到数组处理 IFS=',' read -ra arr <<< "$line" echo "第一个元素:${arr[0]}" echo "处理第三个元素:${arr[2]}" ((index++)) done
配合进程替换的用法(重点)
进程替换<(command)的作用是把命令的输出模拟成一个临时文件,供readarray读取,适合处理动态生成的内容(比如命令过滤后的结果、文件内容)。
正确写法是用< <(command),第一个<是重定向符号,第二个<(command)是进程替换生成的临时“文件”路径:
# 示例:读取data.txt文件内容到数组(data.txt内容就是目标三行文本) readarray -t lines < <(cat data.txt) # 用for循环遍历数组处理(while循环也适用) for line in "${lines[@]}"; do IFS=',' read -ra arr <<< "$line" echo "ID: ${arr[0]}, 标识: ${arr[1]}, 信息: ${arr[2]}" # 对信息字段做md5sum(-n避免echo加多余换行) echo -n "${arr[2]}" | md5sum done
为什么不能直接写readarray -t lines <(cat data.txt)?因为readarray默认从标准输入读取,或者需要指定文件路径,进程替换的结果是一个类似/dev/fd/63的临时文件描述符,必须通过重定向符<指向它才能被readarray识别。
方案3:简洁的awk实现
如果只是处理逗号分隔的字段,awk语法更简洁,无需手动分割数组:
awk -F ',' '{ print "当前行:" $0 print "第二个字段:" $2 # 对第三个字段执行md5sum并获取结果 "echo -n " $3 " | md5sum" | getline md5_result print "第三个字段的md5:" md5_result }' <<HEREDOC 1,a,info 2,b,inf 3,c,in HEREDOC
如果处理文件,直接替换为awk -F ',' '...' data.txt即可。
内容的提问来源于stack exchange,提问作者Summer-Sky
相关产品推荐
相关产品推荐

