4. BLAST 数据库构建:从开始到跑通
好,咱们今天聊聊数据库构建。BLAST 跑得快不快,结果好不好,很大程度上取决于你身后那个数据库靠不靠谱。
我自己入行那会儿,第一件事就是把 NR 数据库全量下载下来。嗯,结果硬盘直接爆了。那之后我才明白,数据库构建不是简单跑条命令,你得先想清楚:查什么?怎么查?查多大?
4.1 makeblastdb:最简单的入门
不管你是用官方数据库还是自己造的序列,第一步永远是 makeblastdb。这工具是 BLAST+ 套件自带的,装好 BLAST 就能用。
基本用法特别直接。假设你手里有个 FASTA 文件 my_seqs.fasta,想把它变成 BLAST 能查的库:
makeblastdb -in my_seqs.fasta -dbtype nucl -out my_db
这里 -dbtype 后面跟两个值:
- nucl:核酸序列。主要用于 blastn、tblastn。
- prot:蛋白序列。用于 blastp、blastx。
-out 参数指定输出库的名字。我个人习惯把库名写得有意义,比如 human_refseq_rna_2024,这样过几个月回头还能想起这是啥。
-max_file_sz 参数。比如 -max_file_sz 4GB,表示单个索引文件的最大尺寸,超过就会分卷。这能避免系统文件大小限制。
4.2 关键参数,一次讲透
别看 makeblastdb 命令短,里面门道不少。我搞过不少次因为漏参数导致结果出错的,咱一次性避开这些坑。
| 参数 | 作用 | 我的踩坑记录 |
|---|---|---|
-dbtype |
指定核酸/蛋白 | 记得把 nucl 拼对,我打成 nucl 也见过别人打成 nucleotide,会报错。 |
-title |
为数据库起个名称 | 如果你建的库很多,有个好标题方便后续管理。建议体现物种、版本、来源。 |
-parse_seqids |
解析序列 ID | 默认不解析,但如果你后续要用 blastdbcmd 提取子集,就必须加这参数。 |
-hash_index |
构建哈希索引 | 用于 blastdb_aliastool,一般用户用不到,但做大规模整合时很实用。 |
举个例子,一个更完整的命令:
makeblastdb -in zebrafish_protein.faa \
-dbtype prot \
-title "Danio rerio RefSeq protein" \
-parse_seqids \
-out zebrafish_refseq_prot
这样建出来的库,后期你用它做任何查询,都能直接从结果反查回原始序列,非常方便。
-parse_seqids,你的 blastdbcmd 没法根据序列 ID 提取信息,整个库就是个“黑盒”。我曾经因为这个,浪费了一天时间批量改代码。
4.3 NT 与 NR:官方两大护法
咱们做质控,经常需要用到官方的 NT 或 NR 库。这两个库到底选哪个?你想想看,你的核心问题是什么?
| 库 | 全称 | 内容 | 典型场景 |
|---|---|---|---|
| NT | Nucleotide collection | 所有已知核酸序列,含冗余 | 物种分类、污染检测、组装后验证 |
| NR | Non-redundant protein | 蛋白质序列,去冗余 | 功能注释、同源性搜索、比较基因组 |
实践中我自己的习惯:
- 做污染检测(比如质控、去除宿主污染)→ 选 NT。因为 NT 含冗余,对低丰度污染的敏感度很高。
- 做功能注释(比如给新组装基因做 blastx)→ 选 NR。去冗余后,结果更容易聚焦在最相关的 hit。
下载策略
NT 和 NR 官方提供了预构建的 BLAST 数据库,直接下载后解压就能用,不用自己跑 makeblastdb。下载地址去 NCBI FTP,但具体链接我建议你别死记,可以写个脚本自动拉。
我记得有一次项目急,我直接手动下载 NT 库,300多GB,下到一半网络断了。哎,后来我就学会用 wget -c(断点续传)配合序列化了。
wget -c ftp://ftp.ncbi.nlm.nih.gov/blast/db/FASTA/nt.gz
gunzip nt.gz
makeblastdb -in nt -dbtype nucl -title "NT full" -parse_seqids -out nt_full
当然,官方数据库更推荐直接下载 .tar.gz 格式的分卷包:
wget -r -np -nd ftp://ftp.ncbi.nlm.nih.gov/blast/db/nt.*.tar.gz
for f in nt.*.tar.gz; do tar xzf "$f"; done
这样你得到的就是已经做好的 BLAST 库,直接 blastn -db nt 就能用。
4.4 自定义数据库:你想查什么就建什么
官方库虽然强大,但还是有局限性。比如你工作在小鼠的肠道宏基因组,那 NT 里的水稻、拟南芥、人源序列就是你不需要的干扰项。这时候,自定义数据库就派上用场了。
说句实话,我做过的商业项目,90% 都用了自定义库。好处很明显:
- 体积小:搜索速度快得多
- 特异性高:干扰序列少,结果更干净
- 可重复利用:团队共享,统一规范
怎么构建?直接套用 makeblastdb
假设你要建一个小型病毒库,包含几十条序列:
cat virus1.fasta virus2.fasta virus3.fasta > my_virus_db.fasta
makeblastdb -in my_virus_db.fasta -dbtype nucl -title "My Virus DB" -out my_virus_db -parse_seqids
就这么简单。关键是你要保证输入序列质量:
- 去除低质量序列(尤其短于 100bp 的,容易导致假阳性)
- 去除重复 ID,否则
-parse_seqids会报错 - 序列行不要带空格或特殊字符,NCB 的格式要求严格
-dbtype prot 加上。有时候交叉验证,把核酸翻译成蛋白再建库去做 blastx,结果更精确。我曾在一个宏基因组项目里,用 nt 库扫出大量“未知”,换成自定义病毒蛋白库,直接命中率飙升到 85%。
一个真实案例
早些年我做过一个临床微生物检测平台。医院想快速判断样本中是否含耐药基因。建一个自定义的耐药基因蛋白库,配合 blastx,整个流程从原来 3 小时缩到 20 分钟,且假阳性率很低。
流程大致是:
- 从 CARD、ResFinder、ARG-ANNOT 下载所有耐药蛋白序列
- 去冗余(用 cd-hit 或 USearch,聚类 90% 以上序列)
- 合并为一个 FASTA
- makeblastdb 建库
- 每天晚上增量更新
这套流程至今仍是我推荐给客户的标配方案。
4.5 库维护与更新策略
数据库不是建完就完事了。我个人的经验是:
- 官方库每 2-3 个月更新一次,不要太频繁,因为全量下载太慢。增量更新可以用 NCBI 的
update_blastdb.pl脚本。 - 自定义库每次有新数据或新版本时重建,但注意保持库名与版本对应,建议在库名里加日期或版本号。
4.6 核心流程图
嗯,这张图基本概括了数据库构建的选择逻辑。你照着走,不会迷路。
4.7 常见问题与避坑
gunzip -t 确认完整性。坑2:自定义库序列 ID 重复。 这会导致
-parse_seqids 报错或查询结果混乱。解决:建库前用 grep '^>' 检查重复 ID,必要时加前缀分群。
blastdb_aliastool 做多库联合查询。这样后续维护、更新都清晰。我曾经把所有细菌序列放一个库,后来想删掉某个属的序列,哎,根本没法做,只能重建整个库。