🔍 nf-core/methylong 内置 DMR 选项:能替代哪些独立工具?
✅ 简短回答
| 您之前需要的功能 | methylong 内置选项 | 能否替代独立工具? |
|---|---|---|
| 位点水平差异分析 (对标 TRANSIT ANOVA) | --population_dmrer dss + --dmr_a/--dmr_b |
✅ 完全可以替代独立 DSS |
| 区域水平聚合比较 | --population_dmrer dss (自动区域聚合) |
✅ 部分替代 methylKit |
| 连续低/高甲基化区域检测 (对标 Tn5Gaps) | ❌ 无专门功能 | ❌ 仍需 metilene 或自定义脚本 |
| 基因/操纵子注释关联 | ❌ 不直接整合 GFF | ❌ 仍需 bedtools/ChIPseeker |
| 出版级可视化 | ❌ 只输出 bed/bigWig | ❌ 仍需 pyGenomeTracks/IGV |
🎯 核心结论:methylong 的
--population_dmrer dss可以完全替代您独立运行 DSS 进行组间差异甲基化分析,无需额外工具!
📋 methylong DMR 选项详解 (对标 TRANSIT)
🔹 参数功能映射表
| methylong 参数 | 作用 | TRANSIT 对应功能 | 统计方法 |
|---|---|---|---|
--skip_snvs |
跳过 SNP calling + phasing | – (细菌无需) | – |
--haplotype_dmrer [dss/modkit] |
单倍型水平 DMR 工具 | – (细菌无单倍型) | 贝叶斯层次模型 (DSS) |
--population_dmrer [dss/modkit] |
⭐ 群体水平 DMR 工具 | ✅ ANOVA 多组比较 | 贝塔 – 二项检验 + FDR |
--dmr_population_scale |
启用多样本组间比较 | ✅ 条件间差异分析 | 同上 |
--dmr_a, --dmr_b |
定义两个比较组的样本名 | ✅ 指定对比条件 | – |
🚀 用 methylong 内置 DSS 替代独立运行的完整命令
场景:细菌 6mA,An6 vs BG5 差异分析
nextflow run nf-core/methylong \
-r 2.0.0 \
-profile docker \
--input samplesheet_6mA.csv \ # 包含 An6 和 BG5 两行
--outdir methylome_out_6mA \
--ont_aligner minimap2 \
--m6a \
--skip_snvs \ # 细菌无需 phasing
--dmr_population_scale \ # ⭐ 启用群体水平比较
--population_dmrer dss \ # ⭐ 使用 DSS 进行统计 (默认值,可省略)
--dmr_a "An6" \ # ⭐ 定义组 A (samplesheet 中的 group 列)
--dmr_b "BG5" \ # ⭐ 定义组 B
-resume \
-work-dir methylome_out_6mA/work
🔹 samplesheet_6mA.csv 格式要求
group,sample,path,ref,method
An6,An6,/path/An6_6mA_mapped.mod.bam,/path/genome.fa,ont
BG5,BG5,/path/BG5_6mA_mapped.mod.bam,/path/genome.fa,ont
⚠️ 关键:
group列的值 (An6,BG5) 必须与--dmr_a/--dmr_b完全一致!
📁 输出文件:methylong 内置 DMR 结果位置
methylome_out_6mA/
└── results/
└── dmr/
├── population_scale/
│ ├── An6_vs_BG5.DSS_DMLs.tsv # ⭐ 位点水平差异结果 (对标 TRANSIT anova_out.xls)
│ ├── An6_vs_BG5.DSS_DMRs.tsv # 区域水平差异结果
│ └── DSS_summary.html # 简要统计摘要
└── qc/
└── dmr_multiqc_report.html # DMR 分析质控
🔹 DSS_DMLs.tsv 列解读 (对标 TRANSIT ANOVA 输出)
| 列名 | 含义 | TRANSIT 对应列 |
|---|---|---|
chr, pos |
基因组坐标 | Orf, TA_pos |
coverage_A, coverage_B |
两组覆盖深度 | TAs |
mod_count_A, mod_count_B |
两组修饰计数 | Mean_[condition] |
methylation_A, methylation_B |
两组甲基化概率 (0-100) | – |
diff |
甲基化差异 (A – B) | LFC_[condition] |
pval, p.adj |
原始/FDR 校正 p 值 | Pval, Padj |
significant |
是否显著 (FDR20%) | status |
⚠️ methylong 内置 DMR 的局限性 (仍需外部工具的场景)
❌ 无法替代的功能 1:连续区域检测 (对标 Tn5Gaps)
# methylong 输出的是"离散位点"差异,不是"连续非修饰区域"
# 如果您需要检测类似 Tn5Gaps 的"长片段无 6mA 区域",仍需:
metilene \
-i An6.bedgraph BG5.bedgraph \
-g genome.sizes \
-o continuous_dmr.tsv \
-p 0.05 -d 0.2
❌ 无法替代的功能 2:基因/操纵子水平注释
# methylong 不直接整合 GFF 注释
# 如需"哪些基因的 6mA 水平显著改变",仍需:
bedtools intersect -a An6_vs_BG5.DSS_DMLs.tsv -b genome.gff -wa -wb > genes_with_diff_6mA.tsv
❌ 无法替代的功能 3:高级可视化
# methylong 只输出 bed/bigWig,不生成出版级图
# 如需 Circos 式基因组视图,仍需:
pygenometracks --tracks tracks.ini --output final_figure.png
🎯 推荐工作流:methylong 内置 + 最小外部工具
graph LR
A[modkit pileup] --> B[methylong with --population_dmrer dss]
B --> C[An6_vs_BG5.DSS_DMLs.tsv]
C --> D{需要连续区域?}
D -->|是 | E[metilene for continuous DMRs]
D -->|否 | F[直接进入注释]
E & F --> G[bedtools + genome.gff for gene annotation]
G --> H[pyGenomeTracks for visualization]
✅ 最小命令集:
# 1️⃣ 主分析:methylong 内置 DSS (替代独立 DSS 运行)
nextflow run nf-core/methylong ... --dmr_population_scale --dmr_a An6 --dmr_b BG5 ...
# 2️⃣ (可选) 连续区域检测:仍需 metilene
awk '$4 == "a" {printf "%s\t%d\t%d\t%.2f\n", $1, $2, $3, $11}' An6_6mA_raw.bed > An6.bg
metilene -i An6.bg BG5.bg -g genome.sizes -o continuous_dmr.tsv
# 3️⃣ (可选) 基因注释:仍需 bedtools
bedtools intersect -a methylome_out_6mA/results/dmr/population_scale/An6_vs_BG5.DSS_DMLs.tsv \
-b genome.gff -wa -wb > annotated_diff_6mA.tsv
💡 一句话总结
🔑 methylong 内置 DMR 选项可以:
- ✅ 完全替代独立 DSS 进行位点水平差异分析 (
--population_dmrer dss)- ✅ 自动完成:标准化 + 贝塔 – 二项检验 + FDR 校正 + 结果输出
🔑 但仍需外部工具:
- ❌ 连续区域检测 (→
metilene)- ❌ 基因注释关联 (→
bedtools/ChIPseeker)- ❌ 出版级可视化 (→
pyGenomeTracks)🎯 您的最优路径:先用 methylong 内置 DSS 拿到差异位点列表,再按需添加 1-2 个外部工具完成注释和可视化!
如需我帮您编写 samplesheet 或调试 methylong DMR 参数,请随时告知!🚀
🔍 结果分析:非 CG 位点更多是完全合理的!
您的结果 完全符合逻辑,甚至反映了细菌基因组的典型特征。让我详细解释:
📊 您的结果汇总
| 修饰类型 | 位点数量 | 占比 | 生物学解释 |
|---|---|---|---|
| 5mC @ CG | 437 | 33% | 经典 CpG 甲基化 |
| 5mC @ non-CG | 870 | 67% | ⭐ 非 CG 位点更多,正常! |
| 4mC @ CG | 7 | 17% | 4mC 很少在 CG 上 |
| 4mC @ non-CG | 34 | 83% | ⭐ 4mC 偏好非 CG 位点 |
✅ 为什么 non-CG 位点更多?三大原因
🔹 原因 1:序列组成决定数量基数
假设基因组碱基随机分布(各 25%):
所有可能的二核苷酸:16 种 (AA, AC, AG, AT, CA, CC, CG, CT, ...)
其中含 C 的位点:
├─ CG: 1 种 → 占所有 C 位点的 ~25%
├─ CA, CC, CT: 3 种 → 占所有 C 位点的 ~75% ← non-CG 位点天生更多!
因此:即使甲基化概率相同,non-CG 位点数量也会是 CG 的 ~3 倍
🔹 原因 2:细菌甲基化偏好特定非 CG 基序
细菌的限制修饰系统通常靶向 特定回文序列,而非随机 CG:
| 常见细菌甲基化基序 | 修饰类型 | 示例细菌 |
|---|---|---|
GATC |
6mA / 4mC | E. coli Dam 甲基化酶 |
CCWGG |
5mC | H. influenzae Dcm 甲基化酶 |
GANTC |
6mA | Caulobacter CcrM 甲基化酶 |
RCGY |
4mC | 多种细菌 |
→ 如果您的细菌有类似系统,非 CG 位点会被优先甲基化!
🔹 原因 3:--motif C 0 捕获了所有胞嘧啶
您使用的命令:
modkit pileup ... --motif CG 0 --motif C 0 ...
--motif C 0= 检测 每一个胞嘧啶(无论后面是什么碱基)- 因此
m,C,0包含:CG+CA+CC+CT所有 C 位点 - 排除 CG 后,剩余的 non-CG 位点自然更多 ✅
🔬 验证:这些 non-CG 信号是真实的吗?
运行以下命令检查数据质量:
# 1️⃣ 比较 CG vs non-CG 的修饰率分布
echo "=== 5mC 修饰率中位数 ==="
echo -n "CG: "
awk -F'\t' '$4 ~ /^m,CG,/ {print $11}' An6_4mC_5mC_raw.bed | sort -n | awk '{a[NR]=$1} END{print a[int(NR/2)]}'
echo -n "non-CG:"
awk -F'\t' '$4 ~ /^m,C,/ && $4 !~ /^m,CG,/ {print $11}' An6_4mC_5mC_raw.bed | sort -n | awk '{a[NR]=$1} END{print a[int(NR/2)]}'
# 2️⃣ 检查 non-CG 位点的序列背景(提取上游10bp)
# 需要先有基因组 fasta 索引
samtools faidx bacass_out/Medaka/An6-unicycler-medaka_polished_genome.fa
# 提取 non-CG 5mC 位点的序列上下文
awk -F'\t' '$4 ~ /^m,C,/ && $4 !~ /^m,CG,/ && $11 >= 70 && $5 >= 10 {
print $1":"$2+1"-"$2+11
}' An6_4mC_5mC_raw.bed | head -20 > nonCG_sites.txt
# 3️⃣ 用 MEME/HOMER 做 motif 富集(可选)
# 如果 870 个位点富集到特定序列,说明是真实生物学信号!
🎯 分析建议:如何处理这 4 类数据?
✅ 推荐策略:分层分析
# 📁 第一层:核心分析(高置信度 CG 位点)
# 用于主图、主要结论
awk -F'\t' '$4 ~ /^m,CG,/ && $11 >= 70 && $5 >= 10' An6_4mC_5mC_raw.bed > An6_5mC_CG_high.bed
awk -F'\t' '$4 ~ /^21839,CG,/ && $11 >= 50 && $5 >= 10' An6_4mC_5mC_raw.bed > An6_4mC_CG_high.bed
# 📁 第二层:探索性分析(non-CG 位点)
# 用于补充材料、motif 发现
awk -F'\t' '$4 ~ /^m,C,/ && $4 !~ /^m,CG,/ && $11 >= 70 && $5 >= 10' An6_4mC_5mC_raw.bed > An6_5mC_nonCG.bed
awk -F'\t' '$4 ~ /^21839,C,/ && $4 !~ /^21839,CG,/ && $11 >= 50 && $5 >= 10' An6_4mC_5mC_raw.bed > An6_4mC_nonCG.bed
# 📁 第三层:全量数据(用于基因组浏览器)
# 不过滤,供 IGV 可视化
cp An6_4mC_5mC_raw.bed An6_all_modified.bed
📊 可视化建议
| 数据类型 | 推荐图表 | 工具 |
|---|---|---|
| 5mC @ CG | 基因组分布 + 修饰率直方图 | deepTools + ggplot2 |
| 4mC @ non-CG | motif 富集 + 热图 | HOMER + seaborn |
| 两者对比 | Venn 图 + 散点图 | R/ComplexHeatmap |
⚠️ 注意事项:避免重复计数!
由于 m,C,0 包含 m,CG,0,不要简单相加:
# ❌ 错误:直接相加会重复计算 CG 位点
total_5mC = CG_count + nonCG_count # 重复!
# ✅ 正确:只用 C motif 统计全部 5mC
awk -F'\t' '$4 ~ /^m,C,/ && $11 >= 70 && $5 >= 10' An6_4mC_5mC_raw.bed | wc -l
# 或:CG + nonCG(确保互斥)
awk -F'\t' '($4 ~ /^m,CG,/ || ($4 ~ /^m,C,/ && $4 !~ /^m,CG,/)) && $11 >= 70 && $5 >= 10' An6_4mC_5mC_raw.bed | wc -l
🧪 快速诊断脚本(一键运行)
#!/bin/bash
FILE="An6_4mC_5mC_raw.bed"
echo "🔍 数据质量诊断"
echo "================"
echo -e "\n📈 各类型原始行数(无过滤):"
echo "5mC @ CG: $(grep -c 'm,CG,' $FILE)"
echo "5mC @ C: $(grep -c 'm,C,' $FILE)"
echo "4mC @ CG: $(grep -c '21839,CG,' $FILE)"
echo "4mC @ C: $(grep -c '21839,C,' $FILE)"
echo -e "\n📊 修饰率统计 (列11):"
for label in "5mC_CG" "5mC_nonCG" "4mC_CG" "4mC_nonCG"; do
case $label in
"5mC_CG") pattern="^m,CG," ;;
"5mC_nonCG") pattern="^m,C,"; exclude="m,CG," ;;
"4mC_CG") pattern="^21839,CG," ;;
"4mC_nonCG") pattern="^21839,C,"; exclude="21839,CG," ;;
esac
if [ -n "$exclude" ]; then
stats=$(awk -F'\t' -v p="$pattern" -v e="$exclude" '$4 ~ p && $4 !~ e {print $11}' $FILE | \
awk '{s+=$1; n++} END{if(n>0) printf "n=%d, median=%.2f, mean=%.2f", n, (n%2?$(int(n/2)+1):($(n/2)+$(n/2+1))/2), s/n}')
else
stats=$(awk -F'\t' -v p="$pattern" '$4 ~ p {print $11}' $FILE | \
awk '{s+=$1; n++} END{if(n>0) printf "n=%d, median=%.2f, mean=%.2f", n, (n%2?$(int(n/2)+1):($(n/2)+$(n/2+1))/2), s/n}')
fi
echo "$label: $stats"
done
🎯 结论
✅ 870 > 437 是完全合理的!
非 CG 胞嘧啶在基因组中本就更多,加上细菌甲基化系统常靶向特定非 CG 基序,导致 non-CG 修饰位点数量超过 CG 位点。
下一步建议:
- 用
nonCG_sites.txt做 motif 富集,看看 870 个位点是否聚集在特定序列 - 如果富集到已知细菌甲基化基序(如
GATC),说明信号真实可靠 🔬 - 在论文/报告中明确区分
CG和non-CG分析,避免混淆
需要我帮您写 motif 富集分析脚本,或生成对比图表吗?📈✨