搜索 FASTA 文件时索引超出范围的解决方法
Workaround for index out of range while searching through FASTA file
我正在开发一个程序,让用户输入他们想要在 FASTA 文件中查找的序列,然后程序显示描述行和属于它的序列。
FASTA 可以在 hugheslab.ccbr.utoronto.ca/supplementary-data/IRC/IRC_representative_cdna.fa.gz 找到,它大约是。 87 MB。
我们的想法是首先创建一个包含描述行位置的列表,描述行始终以 > 开头。知道描述行是什么后,您可以在两个描述行之间的行中搜索 search_term。这正是第四段所做的,结果是一个 48425 长的列表,这里是对结果的一个想法:http://imgur.com/Lxy8hnI
现在第五段是在两个描述行之间搜索,我们以第0行和第15行为例,这将是description_list[a]和description_list[a+1] a = 0 和 a+1 = 1,以及 description_list[0] = 0 和 description_list[1] = 15。在这些行之间,if 语句搜索搜索词,如果它找到一个它将 description_list[a] 保存到 start_position_list 中,将 description_list[a+1] 保存到 stop_position_list 中,稍后将使用。
所以你可以想象像 'ATCG' 这样的简单术语会经常出现,这意味着 start_position_list 和 stop_position_list 会有很多重复项,将使用 list(set(start_position_list))
然后对它们进行排序。这样 start_position_list[0] 和 start_position_list[0] 将是 0 和 15,就像这样:http://imgur.com/QcOsuhM,然后可以将其用作要打印的行的范围以显示顺序。
现在,当然,最大的问题是第 15 行,for i in range(description_list[a], description_list[a+1]):
最终会到达 [a+1],而它已经达到 description_list 的最大长度,因此会给出一个列表索引超出范围错误,正如您在此处看到的:http://imgur.com/hi7d4tr
最好的解决方案是什么?仍然有必要遍历所有描述行,我想不出更好的结构来遍历它们?
file = open("IRC_representative_cdna.fa")
file_list = list(file)
search_term = input("Enter your search term: ")
description_list = []
start_position_list = []
stop_position_list = []
for x in range (0, len(file_list)):
if ">" in file_list[x]:
description_list.append(x)
for a in range(0, len(description_list)):
for i in range(description_list[a], description_list[a+1]):
if search_term in file_list[i]:
start_position_list.append(description_list[a])
stop_position_list.append(description_list[a+1])
避免下标越界错误的方法是缩短循环。替换行
for a in range(0, len(description_list)):
来自
for a in range(0, len(description_list)-1):
此外,我认为您可以使用列表理解来构建 description_list
:
description_list = [x for x in file_list if x.startswith('>')]
除了更短之外,它更有效,因为当只有起始字符相关时,它不会对整行进行线性搜索。
这里有一个使用 biopython 包的解决方案,这样就省去了你自己解析 interleaved fasta 的麻烦:
from Bio import SeqIO
file = open("IRC_representative_cdna.fa")
search_term = input("Enter your search term: ")
for record in SeqIO.parse(file, "fasta"):
rec_seq = record.seq
if search_term in rec-seq:
print(record.id)
print(rec-seq)
我不是很清楚您想要的输出是什么,但是可以轻松更改此代码以适应它。
我正在开发一个程序,让用户输入他们想要在 FASTA 文件中查找的序列,然后程序显示描述行和属于它的序列。 FASTA 可以在 hugheslab.ccbr.utoronto.ca/supplementary-data/IRC/IRC_representative_cdna.fa.gz 找到,它大约是。 87 MB。
我们的想法是首先创建一个包含描述行位置的列表,描述行始终以 > 开头。知道描述行是什么后,您可以在两个描述行之间的行中搜索 search_term。这正是第四段所做的,结果是一个 48425 长的列表,这里是对结果的一个想法:http://imgur.com/Lxy8hnI
现在第五段是在两个描述行之间搜索,我们以第0行和第15行为例,这将是description_list[a]和description_list[a+1] a = 0 和 a+1 = 1,以及 description_list[0] = 0 和 description_list[1] = 15。在这些行之间,if 语句搜索搜索词,如果它找到一个它将 description_list[a] 保存到 start_position_list 中,将 description_list[a+1] 保存到 stop_position_list 中,稍后将使用。
所以你可以想象像 'ATCG' 这样的简单术语会经常出现,这意味着 start_position_list 和 stop_position_list 会有很多重复项,将使用 list(set(start_position_list))
然后对它们进行排序。这样 start_position_list[0] 和 start_position_list[0] 将是 0 和 15,就像这样:http://imgur.com/QcOsuhM,然后可以将其用作要打印的行的范围以显示顺序。
现在,当然,最大的问题是第 15 行,for i in range(description_list[a], description_list[a+1]):
最终会到达 [a+1],而它已经达到 description_list 的最大长度,因此会给出一个列表索引超出范围错误,正如您在此处看到的:http://imgur.com/hi7d4tr
最好的解决方案是什么?仍然有必要遍历所有描述行,我想不出更好的结构来遍历它们?
file = open("IRC_representative_cdna.fa")
file_list = list(file)
search_term = input("Enter your search term: ")
description_list = []
start_position_list = []
stop_position_list = []
for x in range (0, len(file_list)):
if ">" in file_list[x]:
description_list.append(x)
for a in range(0, len(description_list)):
for i in range(description_list[a], description_list[a+1]):
if search_term in file_list[i]:
start_position_list.append(description_list[a])
stop_position_list.append(description_list[a+1])
避免下标越界错误的方法是缩短循环。替换行
for a in range(0, len(description_list)):
来自
for a in range(0, len(description_list)-1):
此外,我认为您可以使用列表理解来构建 description_list
:
description_list = [x for x in file_list if x.startswith('>')]
除了更短之外,它更有效,因为当只有起始字符相关时,它不会对整行进行线性搜索。
这里有一个使用 biopython 包的解决方案,这样就省去了你自己解析 interleaved fasta 的麻烦:
from Bio import SeqIO
file = open("IRC_representative_cdna.fa")
search_term = input("Enter your search term: ")
for record in SeqIO.parse(file, "fasta"):
rec_seq = record.seq
if search_term in rec-seq:
print(record.id)
print(rec-seq)
我不是很清楚您想要的输出是什么,但是可以轻松更改此代码以适应它。