我有一个带有以下示例行的文本文件:
40,1,1a,0002,0001,,1234;5678;,027e;0280;
50,1,1a,0001,0004,,,0890;
我想将用逗号或分号分隔的项目从十六进制转换为十进制,但仅适用于第二个字段右侧的字段。左侧的第一和第二字段已经为十进制。字段数各不相同。
我想用bash编写命令以将上面的文件转换为下面的文件:
40,1,26,2,1,,4660;22136;,638;640;
50,1,26,1,4,,,2192;
我该如何实现?我尝试寻找答案已有一段时间,但我确实找不到有效的答案。
答案 0 :(得分:1)
您可以使用awk执行此操作。棘手的部分是使用逗号和分号进行拆分。最简单的方法是先使用逗号分割,然后检查结果子字符串中是否有分号
echo "40,1,1a,0002,0001,,1234;5678;,027e;0280;" | awk --non-decimal-data -F, '
{printf ("%s,%s,",$1,$2)};
{ for(i = 3; i <= NF; i++) {
n = split($i,tmp,";")
{ for(j = 1; j <= (n-1); j++)
if (length(tmp[j]) != 0) {printf ("%d;","0x"tmp[j])}
}
if (length(tmp[j]) != 0) {printf ("%d","0x"tmp[n])}
if (i != NF) {printf (",")}
}
{printf ("\n")}
}'
40,1,26,2,1,,4660;22136;,638;640;
用--non-decimal-data
表示值不是十进制
用-F,
打印前两个值
{printf ("%s,%s,",$1,$2)};
在逗号之间从第三个字段开始遍历子字符串:
for(i = 3; i <= NF; i++)
使用分号字段拆分子字符串,并将该数组存储在tmp数组中:
n = split($i,tmp,";")
遍历子字符串并将十六进制转换为十进制。如果缺少该值,则不打印任何内容(否则将打印0)
{ for(j = 1; j <= (n-1); j++)
if (length(tmp[j]) != 0) {printf ("%d;","0x"tmp[j])}
}
打印没有分号的最后一个值
if (length(tmp[j]) != 0) {printf ("%d","0x"tmp[n])}
如果这不是最后一个字段,请添加逗号作为分隔符:
if (i != NF) {printf (",")}