{"id":51449248,"url":"https://github.com/yifanfeng97/ihcinfer","last_synced_at":"2026-07-05T19:01:06.935Z","repository":{"id":369425339,"uuid":"1289666156","full_name":"yifanfeng97/ihcinfer","owner":"yifanfeng97","description":"Fast patch-based immunohistochemistry (IHC) inference library for whole-slide images (SVS/KFB), powered by DeepLIIF","archived":false,"fork":false,"pushed_at":"2026-07-05T08:31:08.000Z","size":3268,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-07-05T10:06:18.593Z","etag":null,"topics":["cell","ihc","wsi"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/yifanfeng97.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-07-05T03:37:58.000Z","updated_at":"2026-07-05T08:31:07.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/yifanfeng97/ihcinfer","commit_stats":null,"previous_names":["yifanfeng97/ihcinfer"],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/yifanfeng97/ihcinfer","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/yifanfeng97%2Fihcinfer","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/yifanfeng97%2Fihcinfer/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/yifanfeng97%2Fihcinfer/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/yifanfeng97%2Fihcinfer/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/yifanfeng97","download_url":"https://codeload.github.com/yifanfeng97/ihcinfer/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/yifanfeng97%2Fihcinfer/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":35165568,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-07-05T02:00:06.290Z","response_time":100,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cell","ihc","wsi"],"created_at":"2026-07-05T19:01:06.185Z","updated_at":"2026-07-05T19:01:06.927Z","avatar_url":"https://github.com/yifanfeng97.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003ch1 align=\"center\"\u003eihcinfer\u003c/h1\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003cstrong\u003eFast, patch-based IHC whole-slide inference — powered by DeepLIIF.\u003c/strong\u003e\u003cbr/\u003e\n  From IHC glass slide to cell-counting CSVs, heatmaps, and visual overlays — in one command.\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"README_ZH.md\"\u003e中文\u003c/a\u003e ·\n  \u003ca href=\"#whats-new\"\u003eWhat's New\u003c/a\u003e ·\n  \u003ca href=\"#quick-start\"\u003eQuick Start\u003c/a\u003e ·\n  \u003ca href=\"#documentation\"\u003eDocs\u003c/a\u003e ·\n  \u003ca href=\"#benchmarks\"\u003eBenchmarks\u003c/a\u003e\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"https://pypi.org/project/ihcinfer/\"\u003e\n    \u003cimg src=\"https://img.shields.io/pypi/v/ihcinfer.svg?style=for-the-badge\u0026labelColor=1a1a2e\u0026color=3776ab\" alt=\"PyPI version\"\u003e\n  \u003c/a\u003e\n  \u003cimg src=\"https://img.shields.io/badge/python-3.10%2B-3776ab?style=for-the-badge\u0026logo=python\u0026logoColor=white\u0026labelColor=1a1a2e\" alt=\"Python 3.10+\"\u003e\n  \u003cimg src=\"https://img.shields.io/badge/platform-Linux%20%7C%20Windows%20%7C%20macOS-06b6d4?style=for-the-badge\u0026labelColor=1a1a2e\" alt=\"Platform\"\u003e\n  \u003ca href=\"LICENSE\"\u003e\u003cimg src=\"https://img.shields.io/badge/license-MIT-06b6d4?style=for-the-badge\u0026labelColor=1a1a2e\" alt=\"License\"\u003e\u003c/a\u003e\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://raw.githubusercontent.com/yifanfeng97/ihcinfer/main/docs/assets/hero.png\" alt=\"ihcinfer pipeline: WSI → tissue mask → patch inference → heatmap overlay\" width=\"90%\"/\u003e\n\u003c/p\u003e\n\n---\n\n\u003ca name=\"whats-new\"\u003e\u003c/a\u003e\n## 📰 What's New\n\n- **🚀 Unified `ihc` CLI** — one command for `tissue_seg`, `patch_infer`, and `infer`.\n- **🧫 IHC Tissue Segmentation** — default `ihc` mode optimized for immunohistochemistry backgrounds; `clam` mode for H\u0026E.\n- **⚡ Scoring-only Fast Path** — skip intermediate PIL images during WSI inference to lower memory and boost throughput.\n- **⬇️ Automatic Model Download** — the DeepLIIF TorchScript model is downloaded from Zenodo the first time `model_dir` is omitted.\n- **🧩 Cross-chunk Batch Tiling** — large slides are read in chunks and patches are batched across chunk boundaries for better GPU utilization.\n\n---\n\n`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`).\n\n---\n\n\u003ca name=\"core-features\"\u003e\u003c/a\u003e\n## ✨ Core Features\n\n| | Feature | Description |\n|---|---|---|\n| 🔬 | **Whole-slide image support** | Native SVS / KFB reading via OpenSlide and custom readers. |\n| 🧩 | **Patch input** | Batch inference on PNG / JPEG patches or directories. |\n| ⚡ | **Batch GPU inference** | Cross-chunk patch buffer improves GPU utilization on large slides. |\n| 📊 | **Quantitative outputs** | Per-patch total / positive cell counts and positive ratios as CSV + coordinates. |\n| 🗺️ | **Visual outputs** | Heatmaps, H\u0026E thumbnails, overlays, region / patch samples. |\n| 🧠 | **Automatic model loading** | DeepLIIF model auto-downloaded from Zenodo when `model_dir` is omitted. |\n| 🧫 | **Tissue segmentation** | Standalone `ihc` / `clam` tissue masks, no model required. |\n| 🚀 | **Dramatic speedups** | Up to **14.79×** faster than original DeepLIIF for the full GPU pipeline. |\n\n---\n\n\u003ca name=\"what-can-you-do\"\u003e\u003c/a\u003e\n## 🧑‍🔬 What Can You Do With It?\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cb\u003e🩺 Pathologist / Researcher\u003c/b\u003e — Quantify a whole IHC slide\u003c/summary\u003e\n\u003cbr/\u003e\n\n```bash\nihc infer \\\n  --slide_path \"path/to/CD3.svs\" \\\n  --output_dir ./ihc_outputs \\\n  --gpu_ids 0 \\\n  --batch_size 8\n```\n\nProduces `patch_scoring.csv`, `heatmap.jpg`, and `overlay.jpg` for downstream statistical analysis.\n\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cb\u003e🧬 Bioinformatician\u003c/b\u003e — Integrate IHC scoring into a pipeline\u003c/summary\u003e\n\u003cbr/\u003e\n\n```python\nfrom ihcinfer import IHCAnalyzer\nimport pandas as pd\n\nanalyzer = IHCAnalyzer(gpu_ids=[0], batch_size=16)\nresult = analyzer.infer_wsi(\n    slide_path=\"path/to/slide.svs\",\n    output_dir=\"./outputs\",\n)\n\ndf = pd.read_csv(result.csv_path)\n```\n\n`WSIResult` exposes paths to the CSV, heatmap, thumbnail, overlay, and sample directories directly.\n\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cb\u003e💻 Developer\u003c/b\u003e — Embed tissue segmentation or patch inference\u003c/summary\u003e\n\u003cbr/\u003e\n\n```python\nfrom ihcinfer import segment_tissue\n\nmask = segment_tissue(\"slide.svs\", mode=\"ihc\")\nprint(mask.mask.shape)\n```\n\nPatch-level workflow: `ihc patch_infer --input patch.png --output_dir ./out`.\n\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cb\u003e🔒 Offline / HPC User\u003c/b\u003e — Disable auto-download and use a local model\u003c/summary\u003e\n\u003cbr/\u003e\n\n```bash\nexport IHCINFER_MODEL_DIR=\"/path/to/DeepLIIF_Latest_Model\"\nihc infer --slide_path slide.svs --output_dir ./out --model_dir \"$IHCINFER_MODEL_DIR\"\n```\n\nIn Python, set `auto_download=False`.\n\n\u003c/details\u003e\n\n---\n\n\u003ca name=\"supported-platforms\"\u003e\u003c/a\u003e\n## 📋 Supported Platforms \u0026 Inputs\n\n| Platform | Python | Notes |\n|---|---|---|\n| Linux | 3.10+ | Primary development and test platform. |\n| Windows | 3.10+ | OpenSlide binaries installed automatically via `openslide-bin`. |\n| macOS | 3.10+ | Requires OpenSlide to be installed on the system. |\n\n| Input type | Formats | Usage |\n|---|---|---|\n| Whole-slide images | SVS, KFB | `ihc infer`, `ihc tissue_seg`, `IHCAnalyzer.infer_wsi()` |\n| Patch images | PNG, JPEG | `ihc patch_infer`, `IHCAnalyzer.infer_patches()` |\n\n**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.\n\n---\n\n\u003ca name=\"quick-start\"\u003e\u003c/a\u003e\n## ⚡ 30-Second Quick Start\n\n```bash\n# Install\npip install ihcinfer\n\n# 1. Tissue segmentation (no model required)\nihc tissue_seg --input \"slide.svs\" --output_dir ./tissue_mask --overlay\n\n# 2. Patch inference\nihc patch_infer --input patch.png --output_dir ./patch_outputs\n\n# 3. Whole-slide IHC inference\nihc infer --slide_path slide.svs --output_dir ./ihc_outputs --gpu_ids 0\n```\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cb\u003e🐍 Prefer the Python API?\u003c/b\u003e Click to expand\u003c/summary\u003e\n\u003cbr/\u003e\n\n```python\nfrom ihcinfer import IHCAnalyzer\n\nanalyzer = IHCAnalyzer(\n    model_dir=\"/path/to/DeepLIIF_Latest_Model\",  # omit to auto-download\n    gpu_ids=[0],\n    batch_size=16,\n)\n\nresult = analyzer.infer_wsi(\n    slide_path=\"/path/to/slide.svs\",\n    output_dir=\"/path/to/output\",\n)\n\nprint(result.csv_path)\nprint(result.heatmap_path)\nprint(f\"Region samples: {len(result.region_sample_paths) // 2}\")\nprint(f\"Patch samples: {len(result.patch_sample_dirs)}\")\n```\n\n\u003c/details\u003e\n\n---\n\n\u003ca name=\"python-api\"\u003e\u003c/a\u003e\n## 🐍 Python API\n\n`IHCAnalyzer` is the unified entry point for most users:\n\n```python\nfrom ihcinfer import IHCAnalyzer\n\nanalyzer = IHCAnalyzer(gpu_ids=[0], batch_size=16)\n\n# Whole-slide inference\nresult = analyzer.infer_wsi(\"slide.svs\", output_dir=\"./outputs\")\n\n# Patch inference\npatch_result = analyzer.infer_patches([\"p1.png\", \"p2.png\"], output_dir=\"./patch_outputs\")\n\n# Tissue segmentation\nmask = analyzer.segment_tissue(\"slide.svs\", mode=\"ihc\")\n```\n\n---\n\n\u003ca name=\"why-ihcinfer\"\u003e\u003c/a\u003e\n## 🚀 Why ihcinfer?\n\n| Metric | Original DeepLIIF | ihcinfer | Speedup |\n|---|---|---|---|\n| Full patch pipeline (CPU, 4 patches) | 28.54 s | 19.50 s | **1.46×** |\n| Inference only (GPU) | 1.75 s | 0.55 s | **3.17×** |\n| Full patch pipeline (GPU) | 10.21 s | 0.69 s | **14.79×** |\n| WSI end-to-end (1453 patches, GPU, estimated) | ~10 min | ~4 min | **~2.5–3×** |\n\nTest environment: 6× NVIDIA RTX 3090 / 24 GiB. Reproduction scripts are in [`benchmarks/`](benchmarks/).\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://raw.githubusercontent.com/yifanfeng97/ihcinfer/main/docs/assets/bench_patch_times_en.png\" alt=\"Patch-level time comparison\" width=\"32%\"/\u003e\n  \u003cimg src=\"https://raw.githubusercontent.com/yifanfeng97/ihcinfer/main/docs/assets/bench_wsi_throughput_en.png\" alt=\"WSI throughput comparison\" width=\"32%\"/\u003e\n  \u003cimg src=\"https://raw.githubusercontent.com/yifanfeng97/ihcinfer/main/docs/assets/bench_speedup_en.png\" alt=\"Speedup over original DeepLIIF\" width=\"32%\"/\u003e\n\u003c/p\u003e\n\n\u003e Charts generated by [`benchmarks/plot_benchmarks.py`](benchmarks/plot_benchmarks.py) from the table above.\n\n---\n\n\u003ca name=\"pipeline-architecture\"\u003e\u003c/a\u003e\n## 🏗️ Pipeline Architecture\n\n```mermaid\ngraph LR\n    A[WSI: SVS / KFB] --\u003e B[Tissue Segmentation\u003cbr/\u003eihc / clam mode]\n    B --\u003e C[Chunked Patch Tiler]\n    C --\u003e D[DeepLIIF Batch Inference]\n    D --\u003e E[Cell Scoring]\n    E --\u003e F[CSV + Heatmap]\n    E --\u003e G[H\u0026E Thumbnail + Overlay]\n    E --\u003e H[Region / Patch Samples]\n```\n\n---\n\n\u003ca name=\"documentation\"\u003e\u003c/a\u003e\n## 📚 Documentation \u0026 Resources\n\n| Resource | Link | Description |\n|---|---|---|\n| Example scripts | [`examples/`](examples/) | Patch inference, WSI inference, and tissue-segmentation examples |\n| CLI details | [`examples/README.md`](examples/README.md) | `ihc` command and subcommand reference |\n| Benchmarks | [`benchmarks/`](benchmarks/) | Reproducible comparisons against original DeepLIIF |\n\n---\n\n\u003ca name=\"cli-reference\"\u003e\u003c/a\u003e\n## 🛠️ CLI Reference\n\n```bash\nihc --help\n\n# Subcommands\nihc tissue_seg --input \u003cslide\u003e --output_dir \u003cdir\u003e [--overlay] [--mode ihc|clam]\nihc patch_infer --input \u003cpatch_or_dir\u003e --output_dir \u003cdir\u003e [--model_dir \u003cdir\u003e]\nihc infer --slide_path \u003cslide\u003e --output_dir \u003cdir\u003e [--gpu_ids 0] [--batch_size 8]\n```\n\n---\n\n\u003ca name=\"advanced-usage\"\u003e\u003c/a\u003e\n## 🔧 Advanced Usage\n\n```python\nfrom ihcinfer.inference import PatchInference, RegionInference\nfrom ihcinfer.models import DeepLIIFModel\nfrom ihcinfer.prep import Tiler, TissueSegmenter, segment_tissue\nfrom ihcinfer.readers import create_reader\nfrom ihcinfer.scoring import compute_scoring, extract_cells\nfrom ihcinfer.outputs import build_patch_output, save_patch_output, build_heatmap\n```\n\n---\n\n\u003ca name=\"benchmarks\"\u003e\u003c/a\u003e\n## 📈 Benchmarks\n\nAll numbers can be reproduced with the scripts in [`benchmarks/`](benchmarks/):\n\n```bash\n# Patch-level comparison (original DeepLIIF repo must be on PYTHONPATH)\nPYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_patch_vs_original.py --device cuda:0\n\n# Region-level comparison\nPYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_region_inference.py\n\n# WSI 50-patch comparison\nPYTHONPATH=/path/to/DeepLIIF uv run python benchmarks/bench_wsi_50_vs_original.py\n\n# Full IHC WSI pipeline timing\nuv run python examples/infer_ihc.py \\\n  --slide_path /path/to/slide.svs \\\n  --output_dir ./ihc_outputs \\\n  --gpu_ids 0 --batch_size 8 \\\n  --patch_size 512 --region_size 2048\n```\n\n---\n\n\u003ca name=\"contributing\"\u003e\u003c/a\u003e\n## 🤝 Contributing\n\nIssues and PRs are welcome.\n\n---\n\n\u003ca name=\"license\"\u003e\u003c/a\u003e\n## 📄 License\n\nThis project is licensed under the [MIT](LICENSE) License.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fyifanfeng97%2Fihcinfer","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fyifanfeng97%2Fihcinfer","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fyifanfeng97%2Fihcinfer/lists"}