如何选择并将没有空格分隔的列复制到新文件?

如何选择并将没有空格分隔的列复制到新文件?

我已看到您的 (jcbermu) 脚本,其中介绍了如何选择列并复制到新文件。如果所有列都以空格分隔,则效果会很好(任何数量的空格都可以)。我想改进游览脚本,使其适用于具有以下特殊格式的文件:

  • 第一行有每列的标题(animalid snp1 snp2 等),它们以空格分隔。
  • 第二个原始数据:第一列有动物ID、空格,然后是所有的 SNP 基因型(每个 SNP 一个细胞),它们都作为一个块放在一起(基因型没有空格分隔)。

那么,如何在脚本中告诉我们在第 1 行和第 1 列之后,我们有未分隔的列数据(每个单元格是一个字段)。

我的文件示例:

animalid snp1 snp2 snp3 snp4 snp5 snp6 snp7 ....... snp8000
fish1 2020121 ....... 2
fish2 0202102 ....... 1
fish3 1201201 ....... 2
.
.
Fish1500 2010211 ...... 1

答案1

使用 awk:

awk 'NR >= 2 {gsub(/./, "& ", $2)} 1' <<DATA
foo bar baz
abc 1234
def 5678
DATA

输出

foo bar baz
abc 1 2 3 4
def 5 6 7 8

答案2

如果我理解正确的话,输入文件是这样的

cat fish-genotypes
animalid snp1 snp2 snp3 snp4 snp5 snp6 snp7 snp8000
fish1 20201212
fish2 02021021
fish3 12012012
Fish1500 20102111

输出如下

animalid snp1 snp2 snp3 snp4 snp5 snp6 snp7 snp8000
fish1    2    0    2    0    1    2    1    2       
fish2    0    2    0    2    1    0    2    1       
fish3    1    2    0    1    2    0    1    2       
Fish1500 2    0    1    0    2    1    1    1

带有 CLI 工具的 Bash 脚本

#!/bin/bash
vert=$(cut -d' ' -f1 fish-genotypes |wc -L)
while read -a line; do
    printf "%-$((vert+1))s" ${line[0]}
    [[ "${line[1]}" =~ [[:alpha:]] ]] && {
        unset line[0]
        header=(${line[@]})
        echo ${header[@]}
        continue
    }
    for ((i=0;i<${#header[@]};i++)) {
        printf "%-$((${#header[i]}+1))s" ${line[1]:i:1}
    }
    echo
done <fish-genotypes

相关内容