Calling Peaks with MACS3: Narrow vs Broad Marks & Input Background Modeling
Calling Peaks with MACS3: Narrow vs Broad Marks & Input Background Modeling
Deep dive into Model-based Analysis of ChIP-Seq (MACS3). Estimating fragment size (d) via sonication shifts, calculating dynamic local Poisson lambda from matched input controls, selecting narrowPeak vs broadPeak modes, setting q-value thresholds, and calculating the Fraction of Reads in Peaks (FRiP).
1. Mathematical Architecture of MACS3
Model-based Analysis of ChIP-Seq (MACS3) models read enrichment along the genome using a Poisson distribution. Because chromatin compaction and sequencing accessibility vary across chromosomes, MACS3 replaces a static global Poisson parameter ($\lambda_{\text{BG}}$) with a dynamic local background parameter ($\lambda_{\text{local}}$):
$$\lambda_{\text{local}} = \max(\lambda_{\text{BG}}, \lambda_{\text{1kb}}, \lambda_{\text{5kb}}, \lambda_{\text{10kb}})$$This dynamic calculation from the matched input control guards against false positives in open chromatin or copy-number amplified regions.
2. Executing MACS3 Peak Calling for Narrow Histone Marks (H3K4me3)
# Call peaks for Huntington's Disease Replicate 1 against matched Input
macs3 callpeak \
-t 03_filtered/HD_Rep1.clean.bam \
-c 03_filtered/HD_Input.clean.bam \
-f BAM \
-g hs \
-n HD_Rep1 \
--outdir 04_peaks/ \
-q 0.05 \
--keep-dup all
# Repeat for all biological replicates
for rep in HD_Rep2 Control_Rep1 Control_Rep2; do
ctrl="Control_Input"
[[ "$rep" =~ "HD" ]] && ctrl="HD_Input"
macs3 callpeak \
-t 03_filtered/${rep}.clean.bam \
-c 03_filtered/${ctrl}.clean.bam \
-f BAM \
-g hs \
-n ${rep} \
--outdir 04_peaks/ \
-q 0.05 \
--keep-dup all
done3. Output File Formats & FRiP Score Quality Control
MACS3 generates three primary files per sample:
${sample}_peaks.narrowPeak: Standard ENCODE 10-column BED format containing peak boundaries, signal value, p-value (-log10), q-value (-log10), and the exact single-base summit coordinate.${sample}_summits.bed: Single-nucleotide peak summits, ideal for transcription factor motif discovery.${sample}_peaks.xls: Tab-delimited summary containing fold-enrichment, coordinates, and statistics.
Fraction of Reads in Peaks (FRiP): Calculated as the total number of reads falling within called peaks divided by total mapped reads. For punctate marks like H3K4me3, high-quality experiments yield $\text{FRiP} \ge 1\%-5\%$.
Common Pitfalls & Troubleshooting Checklist
- Java Heap Exhaustion (GATK / Picard): If processes terminate with
java.lang.OutOfMemoryError, set your environment variable explicitly:export _JAVA_OPTIONS="-Xmx16g -Djava.io.tmpdir=/tmp". - Index Timestamp Mismatch: If tools complain that a BAM index is missing or out of date, regenerate with
samtools index -@ 4 sample.bam. - Conda Channel Conflicts: Avoid ABI incompatibilities between bioconda and conda-forge by setting strict priority:
conda config --set channel_priority strict. - Chromosome Naming Contamination: Always verify whether reference FASTA headers use
chr1or1; divergent naming causes silent alignment drops.