1、ADMET预测简介:XGBoost在ADMET领域的优势与应用场景
1.1 什么是ADMET?为什么它如此关键?
做药物研发的朋友,对ADMET这个词肯定不陌生。它代表的是药物分子在体内的五个核心属性:
- A (吸收) —— 药物能不能被人体有效吸收?
- D (分布) —— 药物进入血液后会跑到哪些组织里去?
- M (代谢) —— 肝脏会不会快速把它分解掉?
- E (排泄) —— 药物最终通过什么途径排出体外?
- T (毒性) —— 药物会不会产生副作用或毒性反应?
这几个属性,说白了就是决定一个候选化合物能不能成为真正药物的生死线。
我记得早些年做项目的时候,有个化合物体外活性非常好,IC50漂亮得不行。结果进了动物实验,肝脏代谢太快,半衰期只有十几分钟。嗯,那种心痛的感觉,做过药的人都能理解。
临床前失败案例中,超过50%是因为ADMET性质不佳。所以在早期筛选阶段就把ADMET问题识别出来,能帮研发团队省下大量时间和经费。
1.2 传统方法的困境:为什么需要机器学习?
传统ADMET预测主要依赖两种手段:
| 方法 | 优势 | 痛点 |
|---|---|---|
| 实验测定 | 数据可靠,金标准 | 成本高、通量低,一个化合物测一遍全套ADMET可能要几周 |
| 规则基方法 (如Lipinski五规则) | 简单快速,零成本 | 过于粗糙,对非口服药物几乎无效 |
你想想看,一个大型化合物库可能有数百万个分子。实验测定只能测几百个。传统规则筛选又会漏掉太多有潜力的分子。我们需要一种既能处理高维数据、又能快速预测的方法。
这就是机器学习派上用场的地方。特别是结构化的分子描述符数据和表格形式的实验数据,XGBoost天然适合处理这类问题。
1.3 为什么是XGBoost?它在ADMET预测中的独特优势
我个人习惯在多个模型之间做对比,但XGBoost一直以来都是我的首选基线。原因有这么几点:
- 处理缺失值的能力 —— ADMET实验数据经常有缺失。有些化合物只测了Caco-2渗透性,没测血浆蛋白结合率。XGBoost的稀疏感知算法对缺失值友好,不需要像神经网络那样做大量插值。
- 特征重要性可解释 —— 做药物研发的人不只是要预测结果,还要知道为什么。XGBoost可以明确告诉你:哪些分子描述符对预测hERG毒性贡献最大。这在调整分子结构时非常有用。
- 小样本下表现稳健 —— 我曾在项目中遇到过一个毒性数据集,只有不到500个分子的标注。用神经网络几乎无法训练,但XGBoost依然给出了可用的预测。你想想看,对于早期研发中常见的几百到几千个样品,这个优势很关键。
- 训练速度快,迭代迅速 —— 做调参的时候,你可能一天要跑几十组参数组合。XGBoost的GPU加速和直方图算法让大规模网格搜索变得可行。
我的经验之谈: 在开始调参之前,先跑一次默认参数的XGBoost模型。这能帮你快速判断当前数据集是否"可预测"。如果默认参数下的性能都不错,说明特征质量好,后续微调会非常顺利。
1.4 核心应用场景:这张图帮你看清全貌
下面这张图总结了XGBoost在ADMET预测中最常用的几个场景。我建议你收藏一下,在实际项目中可以对照着看。
1.5 一个典型的工作流
让我给你描述一下实际项目中,XGBoost是怎么被嵌入到ADMET预测管线中的。我在某次合作项目中就用过这个流程:
- 数据准备 —— 从公共数据库(如PubChem、ChEMBL)或内部实验报告中收集化合物的ADMET标注数据。
- 特征工程 —— 使用RDKit或MOE生成分子描述符。我个人习惯生成200-500个2D描述符,包括拓扑指数、分子量、logP、氢键供体/受体数量等。
- 基线模型 —— 先用XGBoost默认参数跑一个基线。这是判断数据集质量的关键步骤。
- 超参数调优 —— 重点调整
n_estimators、max_depth、learning_rate、subsample和colsample_bytree。这部分内容我会在后面的章节里详细展开。 - 评估与解释 —— 用ROC-AUC、精确率-召回率曲线评估模型。再用XGBoost内置的特征重要性工具来分析哪些分子描述符是决定因素。
下面这段代码是我常用的快速基线脚本,你可以直接拿去用:
import xgboost as xgb
from sklearn.model_selection import train_test_split
from sklearn.metrics import roc_auc_score
# 假设 X 是分子描述符矩阵,y 是ADMET标签(0/1)
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.2, random_state=42
)
# 默认参数基线
model = xgb.XGBClassifier(
n_estimators=100,
max_depth=6,
learning_rate=0.3,
subsample=1.0,
colsample_bytree=1.0,
random_state=42
)
model.fit(X_train, y_train)
y_pred = model.predict_proba(X_test)[:, 1]
print(f"基线 AUROC: {roc_auc_score(y_test, y_pred):.4f}")
注意: 这段代码假设你的标签是二分类的。对于多分类ADMET任务(比如CYP抑制中判断多个亚型),需要在
objective 参数中设置为 multi:softmax 或 multi:softprob。我在最初做多标签任务时就踩过这个坑。
1.6 关于调参,你需要知道的几件事
在正式开始后面的调参内容之前,我想先分享一个认知框架。我曾经走过不少弯路,希望你不用重蹈覆辙:
- 不要一上来就调参 —— 先确保数据质量。我见过有人花了两周调参数,结果发现是训练集和测试集有泄露。先做数据清洗,再谈调参。
- 理解参数的物理意义 —— 比如
max_depth控制树深度,太浅欠拟合,太深过拟合。这个平衡需要在具体数据集上摸索。 - ADMET任务往往是类别不平衡的 —— 比如hERG毒性数据中,有毒的分子通常远少于无毒的。这种情况下,评估指标要慎用准确率,多用AUROC或AUPR。
- 早停法 (Early Stopping) 是你的朋友 —— XGBoost原生支持早停。这不仅能防止过拟合,还能帮你自动确定最佳迭代次数。
一个小技巧: 在调参之前,先用
xgb.cv 做交叉验证,观察不同参数组合下的性能趋势。这比直接跑全量数据要快得多,能帮你快速锁定参数范围。