Csv 读取txt文件的awk脚本

Csv 读取txt文件的awk脚本,csv,awk,Csv,Awk,如何使用awk创建以下输出?我无法为逗号分隔的数据创建循环 awk'{print“echo”$1”\nadd“$2”\n删除“$3”\n列出“$4}”test.txt test.txt 1 abc,bcd xyz,yza qwe,wer 2 abc xyz qwe 3 abc xyz,yza qwe,wer 4 abc,bcd xyz wer 输出: echo 1 add abc add bcd remove xyz remove yza list qwe list wer echo 2 ad

如何使用awk创建以下输出?我无法为逗号分隔的数据创建循环

awk'{print“echo”$1”\nadd“$2”\n删除“$3”\n列出“$4}”test.txt

test.txt

1 abc,bcd xyz,yza qwe,wer
2 abc xyz qwe
3 abc xyz,yza qwe,wer
4 abc,bcd xyz wer
输出:

echo 1
add abc
add bcd
remove xyz
remove yza
list qwe
list wer
echo 2
add abc
remove xyz
list qwe
echo 3
add abc
remove xyz
remove yza
list qwe
list wer
echo 4
add abc
add bcd
remove xyz
list wer

你有两个循环,这就是为什么你有一个问题-你需要在空格上拆分行,但在逗号上拆分子元素

我建议使用
perl

#!/usr/bin/env perl
use strict;
use warnings;

my @actions = qw ( echo add remove list ); 

#iterate the lines    
while ( <DATA> ) {
   #split on whitespace
   my @fields = split; 
   #iterate actions and fields
   foreach my $action ( @actions ) { 
      #split each field on ,
      #print action and field for each. 
      print "$action $_\n" for split ( ",", shift @fields ); 
   }
}

__DATA__
1 abc,bcd xyz,yza qwe,wer
2 abc xyz qwe
3 abc xyz,yza qwe,wer
4 abc,bcd xyz wer
我想这就是你想要的

这可以简化为一个衬里:

perl -ane 'for my $act ( qw ( echo add remove list ) ) { print "$act $_\n" for split ",", shift @F }' test.txt

当我必须对生成的数组进行拆分和循环时,我总是觉得awk失去了一点活力,但这里有一个简单的方法,使用函数添加第二个循环,以便处理空格分隔的字段(它们本身是逗号分隔的值):

$cat test.awk
函数打印全部(标签、值){
拆分(值,v,“,”)

对于(i=1;i不一定推荐,但如果您正在寻找紧凑型,您可以用额外的文本(包括换行符)替换逗号

a = "," $2; b = "," $3; c = "," $4;
gsub(/,/, "\nadd ", a);
gsub(/,/, "\nremove ", b);
gsub(/,/, "\nlist ", c);
print "echo " $1 a b c "\n"

另一种替代方法是两阶段
awk

$ awk '{ print "echo " $1; print "add " $2; print "remove " $3}' file 
  | awk -F'[ ,]' 'NF==3{print $1,$2; print $1,$3;next}1' 
$cat tst.awk
开始{split(“echo add remove list”,name)}
{

对于(fldNr=1;fldNr
awk-F“””{for(i=1;iThanks-karakfa。您能解释一下第二个awk语句吗?它适用于示例输入,但我正在尝试修改我的原始输入。好吧,它假设您将有1或2个子字段。第二个awk按空格和逗号拆分字段。对于2个子字段,NF将为3,将其余字段拆分为两行。这将适用于e示例集,但对于更多的子字段可能更难扩展。如果这是您的输入,循环解决方案可能会更好。我的输入文件中有一行:“abc bcd cde def:fed fed:abc,bcd”我需要将fed:abc,bcd拆分为两行,如:“abc bcd cde def:fed fed:abc”“abc bcd cde def:fed fed:bcd”该死,我对这个问题投了更高的票,因为它似乎写得很好,有简明的样本输入、输出和解决问题的尝试,现在OP的评论显示了一个问题中完全没有的主要要求:-(!我有不止一个解决方案,但我喜欢@karakfa的方法,一行awk脚本。这也有效,但我意识到我有“:”。我将提出一个新问题。感谢大家的支持。
a = "," $2; b = "," $3; c = "," $4;
gsub(/,/, "\nadd ", a);
gsub(/,/, "\nremove ", b);
gsub(/,/, "\nlist ", c);
print "echo " $1 a b c "\n"
$ awk '{ print "echo " $1; print "add " $2; print "remove " $3}' file 
  | awk -F'[ ,]' 'NF==3{print $1,$2; print $1,$3;next}1' 
$ cat tst.awk
BEGIN { split("echo add remove list",names) }
{
    for (fldNr=1;fldNr<=NF;fldNr++) {
        split($fldNr,subFlds,/,/)
        for (subFldNr=1;subFldNr in subFlds; subFldNr++) {
            print names[fldNr], subFlds[subFldNr]
        }
    }
}

$ awk -f tst.awk file
echo 1
add abc
add bcd
remove xyz
remove yza
list qwe
list wer
echo 2
add abc
remove xyz
list qwe
echo 3
add abc
remove xyz
remove yza
list qwe
list wer
echo 4
add abc
add bcd
remove xyz
list wer
awk -F" " '{for(i=1;i<=NF;i++){a[i]=$i;} {print "echo "a[1]"\n""add "a[2]"\nremove "a[3]"\nlist "a[4];}}' filename | awk -F" " '{sub(/,/,"\n"$1" ",$0);print}'