【问题标题】:Distance between matched substrings匹配子串之间的距离
【发布时间】:2017-10-14 01:29:43
【问题描述】:

我有一个染色体序列,必须找到其中的子序列以及它们之间的距离。

例如:

字符串:

AACCGGTTACGTTTGGCCAAACGTTTTTTGGGGAAACCCACGTACGTAAAGCCGGTTAAACGT

子字符串:

ACGT

我必须找出所有出现的ACGT 之间的距离。

【问题讨论】:

  • How do I ask a good question?。 SO 不是代码编写服务。您需要先尝试,然后询问具体问题。当 OP 显然只是希望其他人做他们的工作时,我通常不建议回复帖子。
  • “之间的距离”是什么意思?您希望从这些数据中得到什么结果?

标签: string perl substring distance


【解决方案1】:

您可以通过"ACGT" split 输入字符串,并删除返回数组的第一个和最后一个元素以获取"ACGT" 之间的所有片段。然后计算这个片段的长度:

my $input = "AACCGGTTACGTTTGGCCAAACGTTTTTTGGGGAAACCCACGTACGTAAAGCCGGTTAAACGT";
my @fragments = split("ACGT", $input, -1);
@fragments = @fragments[1..$#fragments - 1];
my @dist_arr = map {length} @fragments;

演示:https://ideone.com/AqEwGu

【讨论】:

    【解决方案2】:

    我通常不建议回答明显是 OP 只是希望其他人完成工作的帖子。但是,已经有一个答案,如果输入字符串过大,使用该答案会出现问题,所以这里有一个使用 Perl 内置函数的答案。

    特殊变量@- 存储模式匹配后的匹配位置。

    use strict;
    use warnings;
    
    use Data::Dumper;
    
    my $string = 'AACCGGTTACGTTTGGCCAAACGTTTTTTGGGGAAACCCACGTACGTAAAGCCGGTTAAACGT';
    
    my @pos;
    
    while ( $string =~ /ACGT/g ) {
        push @pos, $-[0];
    }
    
    my @dist;
    
    for my $i (1 .. $#pos) {
        push @dist, $pos[$i] - $pos[$i - 1];
    }
    
    print Dumper(\@pos, \@dist);
    

    此方法比拆分原始字符串使用更少的内存(如果原始字符串足够大,这可能会出现问题)。它的内存占用可以进一步减少,但我通过分别显示匹配位置的累积和增量的计算来关注清晰度。

    一个悬而未决的问题是您是否想要从字符串开头开始的第一个匹配项的索引。严格来说,“比赛之间的距离”不包括在内。

    use strict;
    use warnings;
    
    use Data::Dumper;
    
    my $string = 'AACCGGTTACGTTTGGCCAAACGTTTTTTGGGGAAACCCACGTACGTAAAGCCGGTTAAACGT';
    
    my @dist;
    my $last;
    
    while ($string =~ /ACGT/g) {
        no warnings 'uninitialized';
        push @dist, $-[0] - $last;
        $last = $-[0];
    }
    
    # Do we want the distance of the first
    # match from the beginning of the string?
    
    shift @dist;
    
    print Dumper \@dist;
    

    当然,也可以使用index,但看起来要丑得多。

    【讨论】:

    • 这就是我要写的。但是我们并不真正知道 OP 的 distance between 是什么意思,他们很可能想要从一个子序列开始到下一个子序列开始的碱基数。
    • 如果是这样的话加4很容易。