How to expand an ambiguous dna sequence

Let's say you have a DNA sequence like this:

AATCRVTAA

      

where R

and V

represent the ambiguous values โ€‹โ€‹of DNA nucleotides, where R

is either A

or G

a V

represents A

, C

orG

Is there a Biopython method for generating all the different combinations of sequences that the above ambiguous sequence might represent?

For example, the output will be:

AATCAATAA
AATCACTAA
AATCAGTAA
AATCGATAA
AATCGCTAA
AATCGGTAA

      

+5


source to share


4 answers


Perhaps a little shorter and faster, since, anyway, this function will be used on very large data:

from Bio import Seq
from itertools import product

def extend_ambiguous_dna(seq):
   """return list of all possible sequences given an ambiguous DNA input"""
   d = Seq.IUPAC.IUPACData.ambiguous_dna_values
   return [ list(map("".join, product(*map(d.get, seq)))) ]

      

Usage map

allows you to execute your loops in C rather than Python. This should be much faster than using simple loops or even list comprehension.

Field trials

With a simple dict as d

instead of the character returnedambiguous_na_values



from itertools import product
import time

d = { "N": ["A", "G", "T", "C"], "R": ["C", "A", "T", "G"] }
seq = "RNRN"

# using list comprehensions
lst_start = time.time()
[ "".join(i) for i in product(*[ d[j] for j in seq ]) ]
lst_end = time.time()

# using map
map_start = time.time()
[ list(map("".join, product(*map(d.get, seq)))) ]
map_end = time.time()

lst_delay = (lst_end - lst_start) * 1000
map_delay = (map_end - map_start) * 1000

print("List delay: {} ms".format(round(lst_delay, 2)))
print("Map delay: {} ms".format(round(map_delay, 2)))

      

Outputs:

# len(seq) = 2:
List delay: 0.02 ms
Map delay: 0.01 ms

# len(seq) = 3:
List delay: 0.04 ms
Map delay: 0.02 ms

# len(seq) = 4
List delay: 0.08 ms
Map delay: 0.06 ms

# len(seq) = 5
List delay: 0.43 ms
Map delay: 0.17 ms

# len(seq) = 10
List delay: 126.68 ms
Map delay: 77.15 ms

# len(seq) = 12
List delay: 1887.53 ms
Map delay: 1320.49 ms

      

It is clear that it is map

better, but only 2 or 3 times better. Perhaps it will be optimized.

+3


source


Eventually I will write my own function:

from Bio import Seq
from itertools import product

def extend_ambiguous_dna(seq):
   """return list of all possible sequences given an ambiguous DNA input"""
   d = Seq.IUPAC.IUPACData.ambiguous_dna_values
   r = []
   for i in product(*[d[j] for j in seq]):
      r.append("".join(i))
   return r 

In [1]: extend_ambiguous_dna("AV")
Out[1]: ['AA', 'AC', 'AG']

      

It allows you to create each template for a given size with



In [2]: extend_ambiguous_dna("NN")

Out[2]: ['GG', 'GA', 'GT', 'GC',
         'AG', 'AA', 'AT', 'AC',
         'TG', 'TA', 'TT', 'TC',
         'CG', 'CA', 'CT', 'CC']

      

Hope this saves time for others!

+3


source


I'm not sure how to do this, but here's with itertools:

s = "AATCRVTAA"
ambig = {"R": ["A", "G"], "V":["A", "C", "G"]}
groups = itertools.groupby(s, lambda char:char not in ambig)
splits = []
for b,group in groups:
    if b:
        splits.extend([[g] for g in group])
    else:
        for nuc in group:
            splits.append(ambig[nuc])
answer = [''.join(p) for p in itertools.product(*splits)]

      

Output:

In [189]: answer
Out[189]: ['AATCAATAA', 'AATCACTAA', 'AATCAGTAA', 'AATCGATAA', 'AATCGCTAA', 'AATCGGTAA']

      

0


source


Another itertools solution:

from itertools import product
import re

lu = {'R':'AG', 'V':'ACG'}

def get_seqs(seq):
    seqs = []
    nrepl = seq.count('R') + seq.count('V')
    sp_seq = [a for a in re.split(r'(R|V)', seq) if a]
    pr_terms = [lu[a] for a in sp_seq if a in 'RV']

    for cmb in product(*pr_terms):
        seqs.append(''.join(sp_seq).replace('R', '%s').replace('V', '%s') % cmb)
    return seqs

seq = 'AATCRVTAA'

print 'seq: ', seq
print '\n'.join(get_seqs(seq))

seq1 = 'RAATCRVTAAR'
print 'seq: ', seq1
print '\n'.join(get_seqs(seq1))

      

Output:

seq:  AATCRVTAA
AATCAATAA
AATCACTAA
AATCAGTAA
AATCGATAA
AATCGCTAA
AATCGGTAA
seq:  RAATCRVTAAR
AAATCAATAAA
AAATCAATAAG
AAATCACTAAA
AAATCACTAAG
AAATCAGTAAA
AAATCAGTAAG
AAATCGATAAA
AAATCGATAAG
AAATCGCTAAA
AAATCGCTAAG
AAATCGGTAAA
AAATCGGTAAG
GAATCAATAAA
GAATCAATAAG
GAATCACTAAA
GAATCACTAAG
GAATCAGTAAA
GAATCAGTAAG
GAATCGATAAA
GAATCGATAAG
GAATCGCTAAA
GAATCGCTAAG
GAATCGGTAAA
GAATCGGTAAG

      

0


source







All Articles