![](/img/trans.png)
[英]How do i convert a three-letter amino acids to single letter in an excel file
[英]How do I convert the three letter amino acid codes to one letter code with python or R?
我有一個fasta文件,如下所示。 我想將三個字母的代碼轉換為一個字母代碼。 我怎么能用python或R做到這一點?
>2ppo
ARGHISLEULEULYS
>3oot
METHISARGARGMET
期望的輸出
>2ppo
RHLLK
>3oot
MHRRM
你的建議將不勝感激!
BioPython已經內置了詞典來幫助完成這些翻譯。 以下命令將顯示可用字典的完整列表:
import Bio
help(Bio.SeqUtils.IUPACData)
您正在尋找的預定義詞典:
Bio.SeqUtils.IUPACData.protein_letters_3to1['Ala']
使用字典查找單字母代碼:
d = {'CYS': 'C', 'ASP': 'D', 'SER': 'S', 'GLN': 'Q', 'LYS': 'K',
'ILE': 'I', 'PRO': 'P', 'THR': 'T', 'PHE': 'F', 'ASN': 'N',
'GLY': 'G', 'HIS': 'H', 'LEU': 'L', 'ARG': 'R', 'TRP': 'W',
'ALA': 'A', 'VAL':'V', 'GLU': 'E', 'TYR': 'Y', 'MET': 'M'}
還有一個簡單的函數可以匹配三個字母代碼和整個字符串的一個字母代碼:
def shorten(x):
if len(x) % 3 != 0:
raise ValueError('Input length should be a multiple of three')
y = ''
for i in range(len(x)/3):
y += d[x[3*i:3*i+3]]
return y
測試你的例子:
>>> shorten('ARGHISLEULEULYS')
'RHLLK'
以下是在R中執行此操作的方法:
# Variables:
foo <- c("ARGHISLEULEULYS","METHISARGARGMET")
# Code maps:
code3 <- c("Ala", "Arg", "Asn", "Asp", "Cys", "Glu", "Gln", "Gly", "His",
"Ile", "Leu", "Lys", "Met", "Phe", "Pro", "Ser", "Thr", "Trp",
"Tyr", "Val")
code1 <- c("A", "R", "N", "D", "C", "E", "Q", "G", "H", "I", "L", "K",
"M", "F", "P", "S", "T", "W", "Y", "V")
# For each code replace 3letter code by 1letter code:
for (i in 1:length(code3))
{
foo <- gsub(code3[i],code1[i],foo,ignore.case=TRUE)
}
結果是 :
> foo
[1] "RHLLK" "MHRRM"
請注意,我更改了變量名稱,因為不允許變量名以R中的數字開頭。
>>> src = "ARGHISLEULEULYS"
>>> trans = {'ARG':'R', 'HIS':'H', 'LEU':'L', 'LYS':'K'}
>>> "".join(trans[src[x:x+3]] for x in range(0, len(src), 3))
'RHLLK'
您只需要將其余條目添加到trans
dict中。
編輯:
要完成其余的trans
,你可以這樣做。 文件table
:
Ala A
Arg R
Asn N
Asp D
Cys C
Glu E
Gln Q
Gly G
His H
Ile I
Leu L
Lys K
Met M
Phe F
Pro P
Ser S
Thr T
Trp W
Tyr Y
Val V
閱讀:
trans = dict((l.upper(), s) for l, s in
[row.strip().split() for row in open("table").readlines()])
您可以嘗試查看並安裝Biopython,因為您正在解析.fasta文件,然后轉換為一個字母代碼。 不幸的是,Biopython只有函數seq3(在包中Bio :: SeqUtils),它與你想要的相反。 IDLE中的示例輸出:
>>>seq3("MAIVMGRWKGAR*")
>>>'MetAlaIleValMetGlyArgTrpLysGlyAlaArgTer'
不幸的是,沒有'seq1'功能(但......)但我認為這可能會對你有所幫助。 至於你的問題,Junuxx是正確的。 創建一個字典並使用for循環以三個塊的形式讀取字符串並進行翻譯。 這是一個類似於他提供的功能,包括所有功能,並處理小案例。
def AAcode_3_to_1(seq):
'''Turn a three letter protein into a one letter protein.
The 3 letter code can be upper, lower, or any mix of cases
The seq input length should be a factor of 3 or else results
in an error
>>>AAcode_3_to_1('METHISARGARGMET')
>>>'MHRRM'
'''
d = {'CYS': 'C', 'ASP': 'D', 'SER': 'S', 'GLN': 'Q', 'LYS': 'K',
'ILE': 'I', 'PRO': 'P', 'THR': 'T', 'PHE': 'F', 'ASN': 'N',
'GLY': 'G', 'HIS': 'H', 'LEU': 'L', 'ARG': 'R', 'TRP': 'W', 'TER':'*',
'ALA': 'A', 'VAL':'V', 'GLU': 'E', 'TYR': 'Y', 'MET': 'M','XAA':'X'}
if len(seq) %3 == 0:
upper_seq= seq.upper()
single_seq=''
for i in range(len(upper_seq)/3):
single_seq += d[upper_seq[3*i:3*i+3]]
return single_seq
else:
print("ERROR: Sequence was not a factor of 3 in length!")
Biopython有一個很好的解決方案
>>> from Bio.PDB.Polypeptide import *
>>> three_to_one('ALA')
'A'
對於你的例子,我將通過這一個班輪解決它
>>> from Bio.PDB.Polypeptide import *
>>> str3aa = 'ARGHISLEULEULYS'
>>> "".join([three_to_one(aa3) for aa3 in [ "".join(g) for g in zip(*(iter(str3aa),) * 3)]])
>>> 'RHLLK'
他們可能批評我這種類型的一個班輪:),但在我內心深處,我仍然愛着PERL。
使用R:
convert <- function(l) {
map <- c("A", "R", "N", "D", "C", "E", "Q", "G", "H", "I",
"L", "K", "M", "F", "P", "S", "T", "W", "Y", "V")
names(map) <- c("ALA", "ARG", "ASN", "ASP", "CYS", "GLU", "GLN",
"GLY", "HIS", "ILE", "LEU", "LYS", "MET", "PHE",
"PRO", "SER", "THR", "TRP", "TYR", "VAL")
sapply(strsplit(l, "(?<=[A-Z]{3})", perl = TRUE),
function(x) paste(map[x], collapse = ""))
}
convert(c("ARGHISLEULEULYS", "METHISARGARGMET"))
# [1] "RHLLK" "MHRRM"
# install.packages("seqinr")
# source("https://bioconductor.org/biocLite.R")
# biocLite("iPAC")
library(seqinr)
library(iPAC)
#read in file
fasta = read.fasta(file = "test_fasta.fasta", seqtype = "AA", as.string = T, set.attributes = F)
#split string
n = 3
fasta1 = lapply(fasta, substring(x,seq(1,nchar(x),n),seq(n,nchar(x),n)))
#convert the three letter code for each element in the list
fasta2 = lapply(fasta1, function(x) paste(sapply(x, get.SingleLetterCode), collapse = ""))
# > fasta2
# $`2ppo`
# [1] "RHLLK"
#
# $`3oot`
# [1] "MHRRM"
my %aa_hash=(
Ala=>'A',
Arg=>'R',
Asn=>'N',
Asp=>'D',
Cys=>'C',
Glu=>'E',
Gln=>'Q',
Gly=>'G',
His=>'H',
Ile=>'I',
Leu=>'L',
Lys=>'K',
Met=>'M',
Phe=>'F',
Pro=>'P',
Ser=>'S',
Thr=>'T',
Trp=>'W',
Tyr=>'Y',
Val=>'V',
Sec=>'U', #http://www.uniprot.org/manual/non_std;Selenocysteine (Sec) and pyrrolysine (Pyl)
Pyl=>'O',
);
while(<>){
chomp;
my $aa=$_;
warn "ERROR!! $aa invalid or not found in hash\n" if !$aa_hash{$aa};
print "$aa\t$aa_hash{$aa}\n";
}
使用此perl腳本將三元組aa代碼轉換為單字母代碼。
對於2017年及以后登陸的人:
這是一個單行Linux bash命令,用於將蛋白質氨基酸三字母代碼轉換為文本文件中的單字母代碼。 我知道這不是很優雅,但我希望這有助於搜索相同的人,並希望使用單行命令。
sed 's/ALA/A/g;s/CYS/C/g;s/ASP/D/g;s/GLU/E/g;s/PHE/F/g;s/GLY/G/g;s/HIS/H/g;s/HID/H/g;s/HIE/H/g;s/ILE/I/g;s/LYS/K/g;s/LEU/L/g;s/MET/M/g;s/ASN/N/g;s/PRO/P/g;s/GLN/Q/g;s/ARG/R/g;s/SER/S/g;s/THR/T/g;s/VAL/V/g;s/TRP/W/g;s/TYR/Y/g;s/MSE/X/g' < input_file_three_letter_code.txt > output_file_single_letter_code.txt
解決上面的原始問題,作為單個命令行:
sed 's/.\{3\}/& /g' | sed 's/ALA/A/g;s/CYS/C/g;s/ASP/D/g;s/GLU/E/g;s/PHE/F/g;s/GLY/G/g;s/HIS/H/g;s/HID/H/g;s/HIE/H/g;s/ILE/I/g;s/LYS/K/g;s/LEU/L/g;s/MET/M/g;s/ASN/N/g;s/PRO/P/g;s/GLN/Q/g;s/ARG/R/g;s/SER/S/g;s/THR/T/g;s/VAL/V/g;s/TRP/W/g;s/TYR/Y/g;s/MSE/X/g' | sed 's/ //g' < input_file_three_letter_code.txt > output_file_single_letter_code.txt
說明:
[1] sed 's/.\\{3\\}/& /g'
將拼寫序列。 它會在每第3個字母后添加一個空格。
[2]管道中的第二個' sed'
命令將獲取上面的輸出並轉換為單字母代碼。 加入任何非標准殘留物作為s/XYZ/X/g;
這個命令。
[3]第三個' sed
'命令, sed 's/ //g'
將刪除空格。
Python 3解決方案。
在我的工作中,煩惱的部分是氨基酸代碼可以指經常出現在PDB / mmCIF文件中的修改后的代碼,如
'TIH' - > 'A'。
因此映射可以超過22對。 Python中的第三方工具就像
Bio.SeqUtils.IUPACData.protein_letters_3to1
無法處理它。 我最簡單的解決方案是使用http://www.ebi.ac.uk/pdbe-srv/pdbechem來查找映射,並在遇到它們時在我自己的函數中將不尋常的映射添加到dict。
def three_to_one(three_letter_code):
mapping = {'Aba':'A','Ace':'X','Acr':'X','Ala':'A','Aly':'K','Arg':'R','Asn':'N','Asp':'D','Cas':'C',
'Ccs':'C','Cme':'C','Csd':'C','Cso':'C','Csx':'C','Cys':'C','Dal':'A','Dbb':'T','Dbu':'T',
'Dha':'S','Gln':'Q','Glu':'E','Gly':'G','Glz':'G','His':'H','Hse':'S','Ile':'I','Leu':'L',
'Llp':'K','Lys':'K','Men':'N','Met':'M','Mly':'K','Mse':'M','Nh2':'X','Nle':'L','Ocs':'C',
'Pca':'E','Phe':'F','Pro':'P','Ptr':'Y','Sep':'S','Ser':'S','Thr':'T','Tih':'A','Tpo':'T',
'Trp':'W','Tyr':'Y','Unk':'X','Val':'V','Ycm':'C','Sec':'U','Pyl':'O'} # you can add more
return mapping[three_letter_code[0].upper() + three_letter_code[1:].lower()]
另一個解決方案是在線檢索映射(但url和html模式可能會隨時間變化):
import re
import urllib.request
def three_to_one_online(three_letter_code):
url = "http://www.ebi.ac.uk/pdbe-srv/pdbechem/chemicalCompound/show/" + three_letter_code
with urllib.request.urlopen(url) as response:
single_letter_code = re.search('\s*<td\s*>\s*<h3>One-letter code.*</h3>\s*</td>\s*<td>\s*([A-Z])\s*</td>', response.read().decode('utf-8')).group(1)
return single_letter_code
為了簡單起見,我在這里直接使用re而不是html解析器。
希望這些可以幫助。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.