https://github.com/yifanfeng97/ihcinfer
Fast patch-based immunohistochemistry (IHC) inference library for whole-slide images (SVS/KFB), powered by DeepLIIF
https://github.com/yifanfeng97/ihcinfer
cell ihc wsi
Last synced: about 1 month ago
JSON representation
Fast patch-based immunohistochemistry (IHC) inference library for whole-slide images (SVS/KFB), powered by DeepLIIF
- Host: GitHub
- URL: https://github.com/yifanfeng97/ihcinfer
- Owner: yifanfeng97
- License: mit
- Created: 2026-07-05T03:37:58.000Z (about 1 month ago)
- Default Branch: main
- Last Pushed: 2026-07-05T08:31:08.000Z (about 1 month ago)
- Last Synced: 2026-07-05T10:06:18.593Z (about 1 month ago)
- Topics: cell, ihc, wsi
- Language: Python
- Homepage:
- Size: 3.12 MB
- Stars: 0
- Watchers: 0
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
ihcinfer
Fast, patch-based IHC whole-slide inference — powered by DeepLIIF.
From IHC glass slide to cell-counting CSVs, heatmaps, and visual overlays — in one command.
中文 ·
What's New ·
Quick Start ·
Docs ·
Benchmarks
---
- **🚀 Unified `ihc` CLI** — one command for `tissue_seg`, `patch_infer`, and `infer`.
- **🧫 IHC Tissue Segmentation** — default `ihc` mode optimized for immunohistochemistry backgrounds; `clam` mode for H&E.
- **⚡ Scoring-only Fast Path** — skip intermediate PIL images during WSI inference to lower memory and boost throughput.
- **⬇️ Automatic Model Download** — the DeepLIIF TorchScript model is downloaded from Zenodo the first time `model_dir` is omitted.
- **🧩 Cross-chunk Batch Tiling** — large slides are read in chunks and patches are batched across chunk boundaries for better GPU utilization.
---
`ihcinfer` is a lightweight Python library for batch immunohistochemistry (IHC) inference on SVS / KFB whole-slide images and PNG / JPEG patches. It reorganizes patch buffering, chunk tiling, tissue-mask pre-filtering, and a scoring-only fast path on top of DeepLIIF's TorchScript model, while exposing both a Python API (`IHCAnalyzer`) and a command-line tool (`ihc`).
---
| | Feature | Description |
|---|---|---|
| 🔬 | **Whole-slide image support** | Native SVS / KFB reading via OpenSlide and custom readers. |
| 🧩 | **Patch input** | Batch inference on PNG / JPEG patches or directories. |
| ⚡ | **Batch GPU inference** | Cross-chunk patch buffer improves GPU utilization on large slides. |
| 📊 | **Quantitative outputs** | Per-patch total / positive cell counts and positive ratios as CSV + coordinates. |
| 🗺️ | **Visual outputs** | Heatmaps, H&E thumbnails, overlays, region / patch samples. |
| 🧠 | **Automatic model loading** | DeepLIIF model auto-downloaded from Zenodo when `model_dir` is omitted. |
| 🧫 | **Tissue segmentation** | Standalone `ihc` / `clam` tissue masks, no model required. |
| 🚀 | **Dramatic speedups** | Up to **14.79×** faster than original DeepLIIF for the full GPU pipeline. |
---
## 🧑🔬 What Can You Do With It?
🩺 Pathologist / Researcher — Quantify a whole IHC slide
```bash
ihc infer \
--slide_path "path/to/CD3.svs" \
--output_dir ./ihc_outputs \
--gpu_ids 0 \
--batch_size 8
```
Produces `patch_scoring.csv`, `heatmap.jpg`, and `overlay.jpg` for downstream statistical analysis.
🧬 Bioinformatician — Integrate IHC scoring into a pipeline
```python
from ihcinfer import IHCAnalyzer
import pandas as pd
analyzer = IHCAnalyzer(gpu_ids=[0], batch_size=16)
result = analyzer.infer_wsi(
slide_path="path/to/slide.svs",
output_dir="./outputs",
)
df = pd.read_csv(result.csv_path)
```
`WSIResult` exposes paths to the CSV, heatmap, thumbnail, overlay, and sample directories directly.
💻 Developer — Embed tissue segmentation or patch inference
```python
from ihcinfer import segment_tissue
mask = segment_tissue("slide.svs", mode="ihc")
print(mask.mask.shape)
```
Patch-level workflow: `ihc patch_infer --input patch.png --output_dir ./out`.
🔒 Offline / HPC User — Disable auto-download and use a local model
```bash
export IHCINFER_MODEL_DIR="/path/to/DeepLIIF_Latest_Model"
ihc infer --slide_path slide.svs --output_dir ./out --model_dir "$IHCINFER_MODEL_DIR"
```
In Python, set `auto_download=False`.
---
## 📋 Supported Platforms & Inputs
| Platform | Python | Notes |
|---|---|---|
| Linux | 3.10+ | Primary development and test platform. |
| Windows | 3.10+ | OpenSlide binaries installed automatically via `openslide-bin`. |
| macOS | 3.10+ | Requires OpenSlide to be installed on the system. |
| Input type | Formats | Usage |
|---|---|---|
| Whole-slide images | SVS, KFB | `ihc infer`, `ihc tissue_seg`, `IHCAnalyzer.infer_wsi()` |
| Patch images | PNG, JPEG | `ihc patch_infer`, `IHCAnalyzer.infer_patches()` |
**Model**: DeepLIIF TorchScript model (~3 GB). It is downloaded automatically from Zenodo the first time `model_dir` is omitted, or you can point to a local copy.
---
```bash
# Install
pip install ihcinfer
# 1. Tissue segmentation (no model required)
ihc tissue_seg --input "slide.svs" --output_dir ./tissue_mask --overlay
# 2. Patch inference
ihc patch_infer --input patch.png --output_dir ./patch_outputs
# 3. Whole-slide IHC inference
ihc infer --slide_path slide.svs --output_dir ./ihc_outputs --gpu_ids 0
```
🐍 Prefer the Python API? Click to expand
```python
from ihcinfer import IHCAnalyzer
analyzer = IHCAnalyzer(
model_dir="/path/to/DeepLIIF_Latest_Model", # omit to auto-download
gpu_ids=[0],
batch_size=16,
)
result = analyzer.infer_wsi(
slide_path="/path/to/slide.svs",
output_dir="/path/to/output",
)
print(result.csv_path)
print(result.heatmap_path)
print(f"Region samples: {len(result.region_sample_paths) // 2}")
print(f"Patch samples: {len(result.patch_sample_dirs)}")
```
---
`IHCAnalyzer` is the unified entry point for most users:
```python
from ihcinfer import IHCAnalyzer
analyzer = IHCAnalyzer(gpu_ids=[0], batch_size=16)
# Whole-slide inference
result = analyzer.infer_wsi("slide.svs", output_dir="./outputs")
# Patch inference
patch_result = analyzer.infer_patches(["p1.png", "p2.png"], output_dir="./patch_outputs")
# Tissue segmentation
mask = analyzer.segment_tissue("slide.svs", mode="ihc")
```
---
| Metric | Original DeepLIIF | ihcinfer | Speedup |
|---|---|---|---|
| Full patch pipeline (CPU, 4 patches) | 28.54 s | 19.50 s | **1.46×** |
| Inference only (GPU) | 1.75 s | 0.55 s | **3.17×** |
| Full patch pipeline (GPU) | 10.21 s | 0.69 s | **14.79×** |
| WSI end-to-end (1453 patches, GPU, estimated) | ~10 min | ~4 min | **~2.5–3×** |
Test environment: 6× NVIDIA RTX 3090 / 24 GiB. Reproduction scripts are in [`benchmarks/`](benchmarks/).
> Charts generated by [`benchmarks/plot_benchmarks.py`](benchmarks/plot_benchmarks.py) from the table above.
---
```mermaid
graph LR
A[WSI: SVS / KFB] --> B[Tissue Segmentation
ihc / clam mode]
B --> C[Chunked Patch Tiler]
C --> D[DeepLIIF Batch Inference]
D --> E[Cell Scoring]
E --> F[CSV + Heatmap]
E --> G[H&E Thumbnail + Overlay]
E --> H[Region / Patch Samples]
```
---
## 📚 Documentation & Resources
| Resource | Link | Description |
|---|---|---|
| Example scripts | [`examples/`](examples/) | Patch inference, WSI inference, and tissue-segmentation examples |
| CLI details | [`examples/README.md`](examples/README.md) | `ihc` command and subcommand reference |
| Benchmarks | [`benchmarks/`](benchmarks/) | Reproducible comparisons against original DeepLIIF |
---
```bash
ihc --help
# Subcommands
ihc tissue_seg --input --output_dir [--overlay] [--mode ihc|clam]
ihc patch_infer --input --output_dir [--model_dir ]
ihc infer --slide_path --output_dir [--gpu_ids 0] [--batch_size 8]
```
---
```python
from ihcinfer.inference import PatchInference, RegionInference
from ihcinfer.models import DeepLIIFModel
from ihcinfer.prep import Tiler, TissueSegmenter, segment_tissue
from ihcinfer.readers import create_reader
from ihcinfer.scoring import compute_scoring, extract_cells
from ihcinfer.outputs import build_patch_output, save_patch_output, build_heatmap
```
---
All numbers can be reproduced with the scripts in [`benchmarks/`](benchmarks/):
```bash
# Patch-level comparison (original DeepLIIF repo must be on PYTHONPATH)
PYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_patch_vs_original.py --device cuda:0
# Region-level comparison
PYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_region_inference.py
# WSI 50-patch comparison
PYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_wsi_50_vs_original.py
# Full IHC WSI pipeline timing
uv run python examples/infer_ihc.py \
--slide_path /path/to/slide.svs \
--output_dir ./ihc_outputs \
--gpu_ids 0 --batch_size 8 \
--patch_size 512 --region_size 2048
```
---
Issues and PRs are welcome.
---
This project is licensed under the [MIT](LICENSE) License.