linux - 如何在终端 Linux 中将列转换为行?但更复杂

标签 linux fedora google-genomics bigdata

如何在终端 Linux 中将列转换为行?但是比较复杂……下面是我的数据的一个例子:

SNP_Name        ID_Animal        Allele        Chr        Position
rs01            215               AB            1            100
rs02            215               AA            2            200
rs03            215               BA            3            300
rs04            215               AA            4            400
rs01            300               AB            1            100
rs02            300               BB            2            200
rs03            300               AA            3            300
rs04            300               AB            4            400
rs01            666               BB            1            100
rs02            666               AA            2            200
rs03            666               AB            3            300
rs04            666               AB            4            400

我想将其转换为以下内容:

SNP_Name     Chr     Position   215(ID_animal)  300(ID_Animal) 666(ID_Animal)
rs01         1       100        AB              AB            BB
rs02         2       200        AA              BB            AA
rs03         3       300        BA              AA            AB
rs04         4       400        AA              AB            AB

ID_animal 行在相应等位基因的列中发生变化。我该怎么做? 但我会为每个 ID_animal 重复 55,000 次。所以,我只想成为 55,000 行和 (animal number+SNP_Name+Chr+Position) 列.

谢谢。

最佳答案

这里的问题是数据量,我不想给出一个全部读入内存然后输出的解决方案。

为此,我想依次解析和输出每个 SNP(rs 编号)的数据,而不是依次为每个动物解析和输出数据。但是数据以错误的顺序提供给我们(按动物排序)。

所以我们要做的第一件事就是按照SNP(第一列)对数据进行排序。我还将同时删除标题行,因为数据转换不需要它。

我假设数据存储在文件 data.in 中:

$ sed '1d' data.in | sort -o data.tmp

我们现在有:

$ cat data.tmp
rs01            215               AB            1            100
rs01            300               AB            1            100
rs01            666               BB            1            100
rs02            215               AA            2            200
rs02            300               BB            2            200
rs02            666               AA            2            200
rs03            215               BA            3            300
rs03            300               AA            3            300
rs03            666               AB            3            300
rs04            215               AA            4            400
rs04            300               AB            4            400
rs04            666               AB            4            400

然后我运行以下命令以产生结果:

$ awk -f script.awk data.tmp >data.new

awk 脚本很长,因此将它放在自己的脚本文件中而不是作为“单行代码”是有意义的:

FNR == 1    {
    # at first line of input

    rsid        = $1;
    chr         = $4;
    pos         = $5;

    c           = 0;
    aid[c]      = $2; # animal ID
    all[c++]    = $3; # allele

    do_header   = 1;  # output header when done parsing this SNP

    next;
}

rsid == $1 {
    # still reading animal ID/allele for this SNP
    aid[c]      = $2;
    all[c++]    = $3;
    next;
}

{
    if (do_header) {
        # output header

        printf("SNP_name\tChr\tPosition\t");
        for (c in aid) {
            printf("%d\t", aid[c]);
        }
        printf("\n");

        do_header = 0;
    }

    # output line with data from previous SNP    
    printf("%s\t%d\t%d\t", rsid, chr, pos);
    for (c in all) {
        printf("%s\t", all[c]);
    }
    printf("\n");

    # store data for this SNP
    rsid        = $1;
    chr         = $4;
    pos         = $5;

    c           = 0;
    aid[c]      = $2;
    all[c++]    = $3;
}

END {
    # output line for last SNP

    printf("%s\t%d\t%d\t", rsid, chr, pos);
    for (c in all) {
        printf("%s\t", all[c]);
    }
    printf("\n");
}

对于给定的输入,这会生成包含以下内容的制表符分隔文件 data.new:

SNP_name    Chr Position    215 300 666
rs01    1   100 AB  AB  BB
rs02    2   200 AA  BB  AA
rs03    3   300 BA  AA  AB
rs04    4   400 AA  AB  AB

注意:这要求所有动物都针对完全相同的 SNP 进行基因分型。每个 SNP 都需要出现相同的动物 ID。没有异常(exception)。

关于linux - 如何在终端 Linux 中将列转换为行?但更复杂,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38326493/

相关文章:

windows - Winlibre - 适用于 Windows 的 Aptitude-Synaptic。那会有用吗?

java - 如何在 Fedora 中保留类似于 Windows 的 Java GUI 外观

fedora - RPM 安装期间 Chkconfig 冲突

php - 无法查看或访问 Laravel 公共(public)文件夹

google-bigquery - Google Cloud/BigQuery/Genomics 数据位置

linux - Matlab 二进制文件不接受其在 shell 中的输入值

linux - 执行由特定编译器创建的二进制文件

java - 32/64 位 eclipse