3. Kraken2原理简介
说实话,Kraken2是我在项目中用得最多的宏基因组快速分类工具之一。它的核心思路很简单:用k-mer的精确匹配代替序列比对。你想想看,比对要算编辑距离、要处理gap、要考虑错配,计算量多大。Kraken2直接放弃了这些,换成查表法——读段拆成小片段,去数据库里找一模一样的,找到了就算数。就这么粗暴,但效果出奇地好。
3.1 核心思想:基于k-mer的精确匹配
传统方法(比如BLAST、Bowtie2)走的是比对路线:把读段往参考基因组上贴,算相似度,允许一定的错配和gap。Kraken2完全不同——它只做精确匹配,一个碱基都不能差。
为什么敢这么干?因为k-mer足够短(默认35 bp),短到在基因组中出现的位置相对唯一。加上宏基因组里物种多、基因组覆盖全,精确匹配已经能捕获足够多的信号。我刚开始接触时觉得这做法太粗糙了,后来跑完一批真实数据才发现,精度完全不输比对方法,速度却快了两个数量级。
一句话总结:Kraken2把分类问题变成了查哈希表的问题。读段来,拆k-mer,查表,投票,出结果。就这么简单。
3.2 k-mer与minimizer
先说k-mer。把一个读段按步长1 bp滑动,切成长度为k的短序列,每个短序列就是一个k-mer。比如一条150 bp的读段,k=35,大概能切出116个k-mer。
读段: ATCGGTACCTAGCTA...(150 bp)
k-mer 1: ATCGGTACCTAGCTA...(1-35 bp)
k-mer 2: TCGGTACCTAGCTAA...(2-36 bp)
...
k-mer 116: ...(116-150 bp)
每个k-mer都要去数据库里查。几百万条读段,每段上百个k-mer,这查表量是天文数字。Kraken2的聪明之处在于引入了minimizer(最小化子)——这是Kraken2相比Kraken1最大的改进。
minimizer的原理:在每个k-mer内部,取所有长度为m的子串,找到字典序最小的那个。所有共享同一个minimizer的k-mer,在数据库里只存一份。这样一来,数据库体积能缩小5-10倍。
我的经验:我在项目中遇到过数据库内存爆掉的情况。当时用的还是Kraken1,标准数据库建下来轻松吃掉70+ GB内存。换成Kraken2之后,同样数据量降到12 GB左右。嗯,从那天起我就再也没回过Kraken1了。
Kraken2默认参数是k=35,m=31。m值控制minimizer的长度,m越大,压缩率越高,但匹配分辨率会下降。一般不建议动这两个参数,默认值已经平衡得很好。
3.3 数据库构建与LCA算法
Kraken2的数据库是什么?说白了就是一个巨大的哈希表:key是minimizer,value是taxon ID。构建流程分三步:
- 收集参考基因组:从NCBI下载所有已知的微生物基因组(细菌、古菌、病毒、真菌等)
- 分割k-mer并计算LCA:把每个基因组切成k-mer,如果一个k-mer出现在多个物种中,取这些物种的最低公共祖先(LCA)作为它的标签
- 建立哈希索引:用minimizer做key,LCA结果做value,建成快速查找表
LCA是这里的关键。举个例子:一个k-mer同时出现在E. coli和Salmonella里,数据库不会把它标成其中任何一个,而是标到它们共同的祖先——肠杆菌科(Enterobacteriaceae)。
k-mer "ATCGCTAG..." 出现在:
- Escherichia coli (taxon 562)
- Salmonella enterica (taxon 28901)
→ LCA = Enterobacteriaceae (taxon 543)
数据库记录: minimizer → taxon 543
我曾经踩过一个坑:以为LCA层级越高越保守、结果越可靠。其实不是。LCA太高会损失分辨率,很多读段只能分到科甚至纲一级。在实际项目中,我习惯同时看分类深度和k-mer覆盖数两个指标,才能判断这个结果是真可靠还是假保守。
注意:数据库的版本直接影响分类结果。NCBI的taxonomy每个月都在更新,同一个物种的taxon ID可能变。我建议固定一个数据库版本做完整项目,不要中途升级。否则前后结果没法对比。
3.4 分类流程
一条读段进入Kraken2后,经历五个阶段。我用一张图把整个流程串起来:
流程看起来简单,但每个步骤都有细节。我特别强调第④步——LCA分类决策。这不是简单的取交集,而是沿着分类树路径做累积投票:每个k-mer匹配到的taxon ID,从根节点到该taxon路径上的所有节点都得到一票。最后从根往下找第一个得票数超过阈值的节点,那就是最终分类。
举例:一条读段有100个k-mer
- 40个匹配到 E. coli
- 30个匹配到 Salmonella
- 20个匹配到 Enterobacteriaceae(LCA)
- 10个未匹配
从根向下:
Bacteria(100票)→ Proteobacteria(90票)
→ Enterobacteriaceae(90票)→ 决策点
如果阈值设为50%,Enterobacteriaceae胜出
读段最终分类:Enterobacteriaceae
个人习惯:我每次跑Kraken2之前,会先用5000条读段试跑一次,看看未分类比例。如果未分类超过30%,说明数据库可能不匹配样本——这时候不用跑全量,先回去补数据库。
3.5 Kraken2的特点
最后说说Kraken2的优缺点。没有万能工具,Kraken2强在速度,但也不是没短板。
| 维度 | Kraken2 | 传统比对方法 |
|---|---|---|
| 速度 | 极快(百万读段/分钟) | 慢(千级读段/分钟) |
| 内存占用 | 标准库~12 GB | 取决于索引,通常更大 |
| 错配容忍度 | 无(精确匹配) | 支持错配和gap |
| 分类分辨率 | 依赖数据库完整性 | 依赖比对覆盖度 |
| 新物种检测 | 弱(只认已知序列) | 相对强 |
| 操作复杂度 | 低(一条命令搞定) | 中高(需多步处理) |
说白了,Kraken2最适合的场景是:已知微生物群体的大规模快速筛查。比如临床样本的病原体快速鉴定、环境样本的群落结构概览。如果样本里可能含有大量新物种或高度变异菌株,那Kraken2就力不从心了——这是精确匹配的天然局限。
警惕:Kraken2的输出看起来很精确(精确到物种级别),但数据库里没有的物种它绝对分不出来。我见过有人拿Kraken2跑深海沉积物样本,结果90%以上未分类,然后来问是不是工具坏了——不是工具坏了,是数据库里根本没有那些深海菌。