Man*_*nde 6 bash shell-script text-processing csv
我有List.csv以下格式的 csv 文件命名:
Location,IP Address,Host Name,Domain,Domain Name, User Name,Manufacturer,Model,System Type, Serial Number, Operating System,RAM (GB),Processor Type,Processor Frequency
H1,xx.xx.xx.xx,PC1,domain.com,DOMAIN,User1,LENOVO,4089AZ8,X86-based PC,L90RA96,Microsoft Windows 7 Professional ,2,Pentium(R) Dual-Core CPU E5800,3.20GHz
H3,xx.xx.xx.xx,PC2,domain.com,DOMAIN,User2,LENOVO,4089AZ8,X86-based PC,L906W3P,Microsoft Windows 7 Professional ,2,Pentium(R) Dual-Core CPU E5800,3.20GHz
H2,xx.xx.xx.xx,PC3,domain.com,DOMAIN,User3,LENOVO,4089A76,X86-based PC,L929410,Microsoft Windows 7 Professional ,2,Pentium(R) Dual-Core CPU E5400,2.70GHz
H2,xx.xx.xx.xx,PC4,domain.com,DOMAIN,User4,Hewlett-Packard,Z800,x64-based PC,SGH007QT16,Microsoft Windows 7 Professional ,12,Intel(R) Xeon(R) CPU W5590,3.33GHz
Run Code Online (Sandbox Code Playgroud)
如果您查看该MODEL列,它会带有一些无法解释模型名称的值。我创建了另一个文件 ,model-list.csv其中包含这些值及其相应的模型名称。它看起来像:
Manufacturer,Value,Model Name
Lenovo, 4089AZ8, ThinkCentre
Lenovo, 4089A76, ThinkCentre
HP, Z800, HP Z800 Workstation
Run Code Online (Sandbox Code Playgroud)
我希望List.csv文件中的值被model-list.csv. 由于文件中有 2900 多个项目,文件中有List.csv大约 150 个项目model-list.csv,我计划使用 bash 脚本来实现这一点,如下所示:
#!/bin/bash
file1="List.csv"
file2="model-list.csv"
outfile="List_out.csv"
stagingfile="List-staging.csv"
rm -f "$outfile" "$stagingfile"
while read line
do
ModelNo=`echo "$line"|awk -F',' '{print $2}'`
ModelName=`echo "$line"|awk -F',' '{print $3}'`
cat "$file1"|grep ",$ModelNo," > "$stagingfile"
if [ -s "$stagingfile" ]
then
while read line1
do
NewLine=`echo "$line1"|sed "s/,${ModelNo},/,${ModelName},/g"`
echo "$NewLine" >> "$outfile"
done < "$stagingfile"
rm -f "$stagingfile"
fi
done < "$file2"
Run Code Online (Sandbox Code Playgroud)
执行上述脚本时,"$outfile"与List.csv.
剧本有问题吗?
您可以awk为此使用:
awk -F',|, ' 'NR==FNR{a[$2]=$3} NR>FNR{$8=a[$8];print}' OFS=',' "$file2" "$file1"
Run Code Online (Sandbox Code Playgroud)
这将读取 model-list.csv,将所有模型及其描述存储到字符串索引数组中(例如a["Z800"] == "HP Z800 Workstation")。然后它读取列表数据,用数组中的描述字符串替换每个模型。
解释:
-F',|, ' - 这将使用正则表达式模式设置字段分隔符,在这种情况下,字段分隔符将是单个逗号,或单个逗号和单个空格。NR==FNR{a[$2]=$3}- NR 是一个 awk 内部变量,它跟踪自程序开始以来读取的总行数。FNR 类似,但会跟踪当前文件已读取的行数。NR==FNRawk 惯用语也是如此,意思是“如果这是要读取的第一个文件”,并且关联的操作是a[$2]=$3将字段 3 的值保存在数组中a,并将字符串索引设置为字段 2 的值。NR>FNR{$8=a[$8];print}'- 与前面类似,但这次只对第一个要读取的文件以外的文件进行操作。对于每一行,我们使用字段 8 的值作为索引在数组中查找值,然后将字段 8 重新分配给数组值。最后,打印整行。OFS=',' "$file2" "$file1" - 将输出字段分隔符设置为逗号(默认为空格),然后按指定顺序读入 2 个文件。