bash 中唯一行的条件问题

issue for condition on unique raws in bash

我想在文件中打印 table 的行,问题是当我使用 readline 时多次重印结果,这是我的输入文件

aa      ,DEC    ,file1.txt
aa      ,CHAR   ,file1.txt    
cc      ,CHAR   ,file1.txt  
dd      ,DEC    ,file2.txt
bb      ,DEC    ,file3.txt
bb      ,CHAR   ,file3.txt 
cc      ,DEC    ,file1.txt

这是我想要的结果:

印于file1.txt

aa#DEC,CHAR
cc#CHAR,DEC

印于file2.txt

dd#DEC

印于file3.txt

bb#DEC,CHAR

这是我的尝试:

(cat input.txt|while read line
do
table=`echo $line|cut -d"," -f1
variable=`echo $line|cut -d"," -f2
file=`echo $line|cut -d"," -f3

echo ${table}#${variable}, 

done ) > ${file}

对于您展示的示例,您能否尝试在 GNU awk 中按照展示的示例进行编写和测试awk

awk '
{
  sub(/^,/,"",)
}
FNR==NR{
  sub(/^,/,"",)
  arr[,]=(arr[,]?arr[,]",":"")
  next
}
((,) in arr){
  close(outputFile)
  outputFile=
  print "#"arr[,] >> (outputFile)
  delete arr[,]
}
'  Input_file  Input_file

说明: 为以上添加详细说明。

awk '                         ##Starting awk program from here.
{
  sub(/^,/,"",)             ##Substituting starting comma in 3rd field with NULL.
}
FNR==NR{                      ##Checking condition FNR==NR will be true when first time Input_file is being read.
  sub(/^,/,"",)             ##Substituting starting comma with NULL in 2nd field.
  arr[,]=(arr[,]?arr[,]",":"") 
##Creating arr with index of 1st and 3rd fields, which has 2nd field as value.
  next                        ##next will skip all further statements from here.
}
((,) in arr){             ##Checking condition if 1st and 3rd fields are in arr then do following.
  close(outputFile)           ##Closing output file, to avoid "too many opened files" error.
  outputFile=               ##Setting outputFile with value of 3rd field.
  print "#"arr[,] >> (outputFile)
##printing 1st field # arr value and output it to outputFile here.
  delete arr[,]           ##Deleting array element with index of 1st and 3rd field here.
}
' Input_file Input_file       ##Mentioning Input_file 2 times here.

您的代码中有几个错误。您可以使用内置的 read 以逗号分隔,括号完全不需要。

while IFS=, read -r table variable file
do
    echo "${table}#${variable}," >>"$file"
done< input.txt

done 之后的重定向中使用 $file 是错误的; shell 想要在定义 file 之前打开要重定向到的文件句柄。但根据您的要求,每一行都应该转到不同的文件。

另请注意quoting fixes and the omission of the useless cat.

使用 Awk 后处理器将具有相同值的字段换行到同一行会很容易,但是您也可以在 Awk 中完成所有这些操作,就像您已经收到的其他答案一样。

这可以一次性完成 gnu awk,如下所示:

awk -F ' *, *' '{
   map[][] = (map[][] == "" ? "" : map[][] ",") 
}
END {
   for (f in map)
      for (d in map[f])
         print d "#" map[f][d] > f
}' file

这将填充此数据:

=== file1.txt ===

aa#DEC,CHAR
cc#CHAR,DEC

=== file2.txt ===

dd#DEC

=== file3.txt ===

bb#DEC,CHAR