【发布时间】:2021-02-04 22:08:44
【问题描述】:
因此,对于这个问题,我将给出两个示例代码块,但略有不同。样本 1 给出正确结果,样本 2 给出错误结果。 此处的正确结果意味着它应该能够读取应该从 csv 文件读取的字段,并仅打印这些字段中存在的字符串的计数。示例代码后的示例如下所示。 请注意,该程序会跳过 CSV 文件中的标题行。
示例 1:
#!/bin/awk -f
BEGIN {
FIELDS_LIST = ARGV[1];
delete ARGV[1];
FS = ", *"
num = split(FIELDS_LIST,arr,",")
for(i in arr)
fields[arr[i]]
}
{
for(i = 1; i <= NF; i++)
{
if(FNR != 1)
if(i in fields)
data[++data_index] = $i
}
}
END {
produce_numbers(data)
PROCINFO["sorted_in"] = "@val_num_desc"
for(i in freq)
printf "%s\t%d\n", i, freq[i]
}
function produce_numbers(sortedarray)
{
n = asort(sortedarray)
for(i = 1 ; i <= n; i++)
{
freq[sortedarray[i]]++
}
return
}
示例 2:
#!/bin/awk -f
BEGIN {
FIELDS_LIST = ARGV[1];
delete ARGV[1];
FS = ", *"
num = split(FIELDS_LIST,arr,",")
for(i in arr)
fields[arr[i]]
}
{
for(i = 1; i <= NF; i++)
{
if(FNR != 1)
if(i in arr) #This is the only line changed, fields was changed to arr
data[++data_index] = $i
}
}
END {
produce_numbers(data)
PROCINFO["sorted_in"] = "@val_num_desc"
for(i in freq)
printf "%s\t%d\n", i, freq[i]
}
function produce_numbers(sortedarray)
{
n = asort(sortedarray)
for(i = 1 ; i <= n; i++)
{
freq[sortedarray[i]]++
}
return
}
代码将使用 ./example-awk.awk 2,3 simple.csv 之类的东西调用,其中包含 simple.csv
Field1,Field2,Field3,Field4
A,V,A,C
B,C,V,D
E,W,C,A
结果应该是
V 2
C 2
A 1
W 1
样本 1 提供了正确的结果,但是样本 2 提供了
A 1
B 1
C 1
E 1
W 1
V 1
显示它仅从字段 1 和 2 读取,而不是从命令行参数指定的 2 和 3。 我想知道为什么在 begin 中创建第二个数组,然后使用它而不是原来的 arr 来解决问题。
【问题讨论】:
-
为什么不打印字段中而不是 arr 中的 i?