如何修改AWK脚本,为CSV中重复名称的初始项添加位置生成登录名?
处理CSV文件生成登录名:重复name字段的初始项也添加位置前缀的解决方案
需求说明
- 当
name字段存在重复时,该name对应的所有条目(包括首次出现的初始项)的login字段需格式化为:小写location+小写name@mail.com - 非重复的
name字段条目,login字段直接使用:小写name@mail.com
原始CSV数据
id,location,name,login 1,KP,Lacie, 2,US,Pamella, 3,CY,Korrie, 4,NI,Korrie, 5,BT,Queenie, 6,AW,Donnie, 7,GP,Pamella, 8,KP,Pamella, 9,LC,Pamella, 10,GM,Ericka,
期望输出结果
id,location,name,login 1,KP,Lacie,lacie@mail.com 2,US,Pamella,uspamella@mail.com 3,CY,Korrie,cykorrie@mail.com 4,NI,Korrie,nikorrie@mail.com 5,BT,Queenie,queenie@mail.com 6,AW,Donnie,donnie@mail.com 7,GP,Pamella,gppamella@mail.com 8,KP,Pamella,kppamella@mail.com 9,LC,Pamella,lcpamella@mail.com 10,GM,Ericka,ericka@mail.com
现有脚本问题
使用以下AWK脚本仅为后续重复项添加了位置前缀,首次出现的重复name条目未添加前缀:
cat data.csv | awk 'BEGIN {FS=OFS=","}; NR > 1 { split($3, name) $4 = tolower($3) split($4, login) for (k in login) { !a[login[k]]++ ? sub(login[k], login[k]"@mail.com", $4) : sub(login[k], tolower($2)login[k]"@mail.com", $4) } }; 1' > data_new.csv
当前错误输出:
id,location,name,login 1,KP,Lacie,lacie@mail.com 2,US,Pamella,pamella@mail.com 3,CY,Korrie,korrie@mail.com 4,NI,Korrie,nikorrie@mail.com 5,BT,Queenie,queenie@mail.com 6,AW,Donnie,donnie@mail.com 7,GP,Pamella,gppamella@mail.com 8,KP,Pamella,kppamella@mail.com 9,LC,Pamella,lcpamella@mail.com 10,GM,Ericka,ericka@mail.com
修改后的解决方案
问题根源是原脚本在第一次遍历的时候无法预知当前name是否会重复,所以需要两次扫描CSV文件:第一次统计每个name的出现次数,第二次根据次数生成对应的login字段。
修改后的AWK脚本:
awk 'BEGIN {FS=OFS=","} # 第一次扫描:统计每个name的出现次数 NR == FNR { if (NR > 1) { name_count[tolower($3)]++ } next } # 第二次扫描:生成login字段 { if (NR == 1) { print $0 next } lower_name = tolower($3) lower_loc = tolower($2) if (name_count[lower_name] > 1) { $4 = lower_loc lower_name "@mail.com" } else { $4 = lower_name "@mail.com" } print $0 }' data.csv data.csv > data_new.csv
脚本说明
- 第一次扫描(NR == FNR):遍历整个CSV,统计每个小写name的出现次数,存储在
name_count数组中 - 第二次扫描:
- 保留表头行直接输出
- 对数据行,先转换name和location为小写
- 检查当前name的出现次数:如果大于1,就生成带location前缀的login;否则生成普通格式的login
- 输出处理后的行
验证结果
运行修改后的脚本后,输出将完全符合期望结果,所有重复name的条目(包括首次出现的)都会添加对应location的小写前缀。
内容的提问来源于stack exchange,提问作者Dmitry Strunewsky
相关产品推荐
相关产品推荐

