- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
我必须使用 awk 处理大量 txt 文件(每个文件有 1600 万行)。例如,我必须阅读十个文件:
文件#1:
en sample_1 200
en.n sample_2 10
en sample_3 10
文件#2:
en sample_1 10
en sample_3 67
文件#3:
en sample_1 1
en.n sample_2 10
en sample_4 20
...
我想要这样的输出:
source title f1 f2 f3 sum(f1,f2,f3)
en sample_1 200 10 1 211
en.n sample_2 10 0 10 20
en sample_3 10 67 0 77
en sample_4 0 0 20 20
这是我的第一个版本的代码:
#! /bin/bash
clear
#var declaration
BASEPATH=<path_to_file>
YEAR="2014"
RES_FOLDER="processed"
FINAL_RES="2014_06_01"
#results folder creation
mkdir $RES_FOLDER
#processing
awk 'NF>0{a[$1" "$2]=a[$1" "$2]" "$3}END{for(i in a){print i a[i]}}' $BASEPATH/$YEAR/* > $RES_FOLDER/$FINAL_RES
这里是我的输出:
en sample_1 200 10 1
en.n sample_2 10 10
en sample_3 10 67
en sample_4 20
我对如何将零列放在未发现事件的地方以及如何获得所有值的总和感到有点困惑。我知道我必须使用这个:
{tot[$1" "$2]+=$3} END{for (key in tot) print key, tot[key]}
希望有人能帮忙。谢谢。
********* 已编辑 ********
我正在尝试以不同的方式实现我的结果。我创建了一个这样的 bash 脚本,它生成了一个包含我所有 key 的排序文件,它非常庞大,大约有 6200 万条记录,我将这个文件分成多个部分,然后将每个部分传递给我的 awk 脚本。
巴什:
#! /bin/bash
clear
FILENAME=<result>
BASEPATH=<base_path>
mkdir processed/slice
cat $BASEPATH/dataset/* | cut -d' ' -f1,2 > $BASEPATH/processed/aggr
sort -u -k2 $BASEPATH/processed/aggr > $BASEPATH/processed/sorted
split -d -l 1000000 processed/sorted processed/slice/slice-
echo $(date "+START PROCESSING DATE: %d/%m/%y - TIME: %H:%M:%S")
for filename in processed/slice/*; do
awk -v filename="$filename" -f algorithm.awk dataset/* >> processed/$FILENAME
done
echo $(date "+END PROCESSING DATE: %d/%m/%y - TIME: %H:%M:%S")
rm $BASEPATH/processed/aggr
rm $BASEPATH/processed/sorted
rm -rf $BASEPATH/processed/slice
AWK:
BEGIN{
while(getline < filename){
key=$1" "$2;
sources[key];
for(i=1;i<11;i++){
keys[key"-"i] = "0";
}
}
close(filename);
}
{
if(FNR==1){
ARGIND++;
}
key=$1" "$2;
keys[key"-"ARGIND] = $3
}END{
for (s in sources) {
sum = 0
printf "%s", s
for (j=1;j<11;j++) {
printf "%s%s", OFS, keys[s"-"j]
sum += keys[s"-"j]
}
print " "sum
}
}
我使用 awk 预分配我的最终数组,并读取 dataset/*
文件夹我填充它的内容。我发现我的瓶颈来自于通过 awk 输入迭代数据集文件夹(10 个文件,每个文件有 16.000.000 行)。一切都在一小部分数据上工作,但对于真实数据,RAM (30GB) 很拥挤。有人有什么建议或建议吗?谢谢。
最佳答案
$ cat tst.awk
{
key = $1" "$2
keys[key]
val[key,ARGIND] = $3
}
END {
for (key in keys) {
sum = 0
printf "%s", key
for (fileNr=1;fileNr<=ARGIND;fileNr++) {
printf "%s%s", OFS, val[key,fileNr]+0
sum += val[key,fileNr]
}
print sum
}
}
$ awk -f tst.awk file1 file2 file3
en sample_4 0 0 2020
en.n sample_2 10 0 1020
en sample_1 200 10 1211
en sample_3 10 67 077
上面使用 GNU awk 作为 ARGIND,其他 awk 只需在开头添加一行 FNR==1{ARGIND++}
。如有必要,将输出通过管道传输到 sort
。
关于linux - 使用awk处理多个文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33978240/
是否可以从 awk 文件执行另一个 awk 文件?使用 awk 文件我需要执行当前文件夹中的所有 awk 文件。是否可以在 awk 中进行此类操作? 最佳答案 是的你可以。您需要使用 system()
这是一个 awk 脚本,它尝试根据第一列设置两个文件的差异: BEGIN{ OFS=FS="\t" file = ARGV[1] while (getline < file)
awk 逐行处理文件。假设每一行操作不依赖于其他行,有没有办法让 awk 一次并行处理多行? 是否有任何其他文本处理工具可以自动利用并行性并更快地处理数据? 最佳答案 唯一试图提供 awk 并行实现的
我有文件: 结果.txt Apple fruits 10 20 30 Car vehicle 40 50 60 Book study 70 80 90 假设这里第 2 列是特征,第 3 列是最小值
就目前而言,这个问题不适合我们的问答形式。我们希望答案得到事实、引用或专业知识的支持,但这个问题可能会引起辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visit the he
我对 awk 的行为感到惊讶表演时浮点数 计算。它导致我对表格数据进行错误计算。 $ awk 'BEGIN {print 2.3/0.1}' 23 0.1}' )。 那么我应该如何执行大于 (
为什么我在下面的例子中得到分隔符前后的空格? awk -F'^' '{print $1,":",$2}' SERVER_2012-02-29-12-15-00 3969 : 1272 3969 :
我有一个文件,其中每四行是这样的: HISEQ15:454:D27KKACXX:6:2316:16241:100283 1:N:0:GTTTCG (对于那些感兴趣的人,此文件包含DNA序列) 我需
你能帮我按 $2 列中的坐标合并行吗?有一系列坐标以一个为单位增长。我想输出 f.e. :第 1 行合并到第 4 行 9079811-9079814,之后没有系列,因此将其合并到另一行等。对于输入中的
大家好,我是 awk 的新手,我可以问一下我有这样的输入文件吗: # ABC DEFG value1 GH value2 GH value3 GH # BCF SQW value4 GH value5
大家好,我想问一下,我对awk中的括号{}感到非常困惑,就像我写了一段代码 { FNR == 3 { print $1 " age is " $2 } } 但它在外括号上给了我错误但没有在打印语
我想知道如何在 awk 中使用多行注释。到目前为止,我一直在使用 # 来评论一行。有人可以就此指导我。谢谢你。 最佳答案 AWK 中没有多行注释,但如果需要,您可以伪造它。这是一种至少适用于 GNU
关于AND逻辑运算符的一个基本问题。我试图根据第1列和第2列的值提取数据文件niveles.csv中的某些字段。我想写一个awk语句,说“当field1 = date和field2 = area然后打
以下命令按预期工作。 # some command | awk '/(\|\|\)/,/;/' create table todel1 (id int) max_rows=2 /*!*/; alter
我有一个日志文件,需要在服务器上“重播”。 它包含这样的条目: Request: query: EXEC prc_insert_customer @param0: 11
如何从制表符分隔的字符串中选择第一列? # echo "LOAD_SETTLED LOAD_INIT 2011-01-13 03:50:01" | awk -F'\t' '{prin
我正在尝试在目录中的多个文件的内容中执行一些 grep 并将我的 grep 匹配附加到单个文件中,在我的输出中我还想要一个包含文件名的列,以了解哪些文件条目已被拾取。我试图使用 awk 来实现相同的目
我想选择文件中第9列的绝对值小于500的行。列有时为正,有时为负。 awk -F'\t' '{ if ($9 output.bam 到目前为止这不起作用..互联网上的一轮告诉我,要使用绝对值,我们应
例如,假设我运行以下命令: gawk -f AppendMapping.awk Reference.tsv TrueInput.tsv 假设文件名会改变。在遍历第一个文件时,我想创建一个映射。 map
我正在使用这个命令; awk -v regex1='new[[:blank:]]+File\(' 'BEGIN{print "Regex1 =", regex1}' 这警告我; awk: warnin
我是一名优秀的程序员,十分优秀!