Carpediem123 commited on
Commit
df22c21
·
verified ·
1 Parent(s): 5b9cd6f

Publish final report and preserve previous report

Browse files
Files changed (3) hide show
  1. README.md +13 -4
  2. index.html +402 -17
  3. previous_report.html +308 -0
README.md CHANGED
@@ -1,10 +1,19 @@
1
  ---
2
- title: Imagebind Pathology Report
3
- emoji: ⚡
4
- colorFrom: blue
5
  colorTo: pink
6
  sdk: static
7
  pinned: false
8
  ---
9
 
10
- Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
 
 
 
 
 
 
 
 
 
1
  ---
2
+ title: ImageBind Pathology Report
3
+ emoji: 🔬
4
+ colorFrom: purple
5
  colorTo: pink
6
  sdk: static
7
  pinned: false
8
  ---
9
 
10
+ # Four-Modal Pathology Bind 实验报告
11
+
12
+ 本 Space 用于呈现 H&E、RNA、mIF 和病理文本四模态对齐项目的最终图文实验报告。
13
+
14
+ - `index.html`:最终报告;
15
+ - `previous_report.html`:旧版报告,供结果追溯和版本比较。
16
+
17
+ 模型、推理与复现代码:`iLOVE2D/fourmodal-pathology-bind`
18
+
19
+ 训练特征和数据划分:`iLOVE2D/fourmodal-pathology-features`
index.html CHANGED
@@ -1,19 +1,404 @@
1
  <!doctype html>
2
- <html>
3
- <head>
4
- <meta charset="utf-8" />
5
- <meta name="viewport" content="width=device-width" />
6
- <title>My static Space</title>
7
- <link rel="stylesheet" href="style.css" />
8
- </head>
9
- <body>
10
- <div class="card">
11
- <h1>Welcome to your static Space!</h1>
12
- <p>You can modify this app directly by editing <i>index.html</i> in the Files and versions tab.</p>
13
- <p>
14
- Also don't forget to check the
15
- <a href="https://huggingface.co/docs/hub/spaces" target="_blank">Spaces documentation</a>.
16
- </p>
17
- </div>
18
- </body>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
19
  </html>
 
1
  <!doctype html>
2
+ <html lang="zh-CN">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1">
6
+ <title>四模态病理嵌入模型</title>
7
+ <link rel="preconnect" href="https://fonts.googleapis.com">
8
+ <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
9
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@600;700&family=Noto+Sans+SC:wght@400;500;700&family=IBM+Plex+Mono:wght@400;500&display=swap">
10
+ <style>
11
+ /* Layout: one reading column (~68ch) with wide tables/figures allowed to break out; H&E stain palette (hematoxylin violet, eosin pink) */
12
+ :root {
13
+ --bg: #fbf9fb;
14
+ --surface: #f3eef4;
15
+ --fg: #231c2b;
16
+ --muted: #675d70;
17
+ --rule: #ddd3e0;
18
+ --hema: #4b3a8c; /* hematoxylin: accent, links, final model */
19
+ --eosin: #c2477a; /* eosin: second series */
20
+ --steel: #7f8aa3; /* neutral series */
21
+ --good: #2f7d5b;
22
+ --warn: #a8641a;
23
+ --bar-track: #ebe4ed;
24
+ --code-bg: #f0eaf2;
25
+ --f-display: "Noto Serif SC", "Songti SC", "STSong", serif;
26
+ --f-body: "Noto Sans SC", "PingFang SC", "Microsoft YaHei", system-ui, sans-serif;
27
+ --f-mono: "IBM Plex Mono", ui-monospace, "SFMono-Regular", Menlo, monospace;
28
+ --step-0: 15px; --step-1: 17px; --step-2: 21px; --step-3: 28px; --step-4: 36px;
29
+ }
30
+ @media (prefers-color-scheme: dark) {
31
+ :root:not([data-theme="light"]) {
32
+ --bg: #17131c; --surface: #211b28; --fg: #ece6f0; --muted: #a99fb3; --rule: #3a3143;
33
+ --hema: #a99af0; --eosin: #ec86b0; --steel: #9aa5bd; --good: #6cc59b; --warn: #e0a35a;
34
+ --bar-track: #2c2434; --code-bg: #241d2b; color-scheme: dark;
35
+ }
36
+ }
37
+ :root[data-theme="dark"] {
38
+ --bg: #17131c; --surface: #211b28; --fg: #ece6f0; --muted: #a99fb3; --rule: #3a3143;
39
+ --hema: #a99af0; --eosin: #ec86b0; --steel: #9aa5bd; --good: #6cc59b; --warn: #e0a35a;
40
+ --bar-track: #2c2434; --code-bg: #241d2b; color-scheme: dark;
41
+ }
42
+ * { box-sizing: border-box; }
43
+ body { background: var(--bg); color: var(--fg); font-family: var(--f-body); font-size: var(--step-0); line-height: 1.75; }
44
+ .wrap { max-width: 980px; margin: 0 auto; padding-inline: 20px; padding-block: 40px 80px; }
45
+ .col { max-width: 42em; }
46
+ header { display: grid; gap: 14px; padding-bottom: 28px; border-bottom: 1px solid var(--rule); }
47
+ .eyebrow { font-family: var(--f-mono); font-size: 12px; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
48
+ h1 { font-family: var(--f-display); font-size: var(--step-4); line-height: 1.25; margin: 0; text-wrap: balance; }
49
+ h2 { font-family: var(--f-display); font-size: var(--step-3); line-height: 1.3; margin: 56px 0 12px; text-wrap: balance; }
50
+ h3 { font-size: var(--step-1); margin: 28px 0 8px; }
51
+ p { margin: 0 0 12px; }
52
+ .lede { font-size: var(--step-1); color: var(--fg); }
53
+ .meta { font-size: 13px; color: var(--muted); }
54
+ a { color: var(--hema); }
55
+ code, .mono { font-family: var(--f-mono); font-size: .9em; }
56
+ code { background: var(--code-bg); padding: 1px 5px; border-radius: 4px; }
57
+ pre.code { background: var(--code-bg); padding: 16px 18px; border-radius: 8px; overflow-x: auto; font-family: var(--f-mono); font-size: 13px; line-height: 1.6; margin: 12px 0 16px; }
58
+ ul, ol { padding-left: 1.3em; margin: 0 0 12px; }
59
+ li { margin: 4px 0; }
60
+ .tbl { overflow-x: auto; margin: 12px 0 18px; }
61
+ table { border-collapse: collapse; width: 100%; font-size: 14px; font-variant-numeric: tabular-nums; }
62
+ th, td { text-align: left; padding: 7px 10px; border-bottom: 1px solid var(--rule); vertical-align: top; }
63
+ th { font-weight: 500; color: var(--muted); font-size: 13px; white-space: nowrap; }
64
+ td.n, th.n { text-align: right; font-family: var(--f-mono); white-space: nowrap; }
65
+ tr.final td { background: var(--surface); font-weight: 500; }
66
+ tr.final td:first-child { box-shadow: inset 3px 0 0 var(--hema); }
67
+ .kind { font-family: var(--f-mono); font-size: 11px; letter-spacing: .04em; padding: 1px 7px; border-radius: 999px; border: 1px solid var(--rule); color: var(--muted); white-space: nowrap; }
68
+ .kind.trained { color: var(--hema); border-color: var(--hema); }
69
+ .kind.emergent { color: var(--eosin); border-color: var(--eosin); }
70
+ .kind.virtual { color: var(--warn); border-color: var(--warn); }
71
+ .ok { color: var(--good); font-weight: 500; }
72
+ .bad { color: var(--warn); font-weight: 500; }
73
+ .note { color: var(--muted); font-size: 13px; }
74
+ .callout { background: var(--surface); border-radius: 8px; padding: 16px 20px; margin: 16px 0; }
75
+ .callout p:last-child { margin-bottom: 0; }
76
+ .panels { display: grid; grid-template-columns: repeat(auto-fit, minmax(270px, 1fr)); gap: 18px; margin: 16px 0 6px; }
77
+ .panel { min-width: 0; }
78
+ .panel h4 { margin: 0 0 6px; font-size: 14px; font-weight: 500; }
79
+ .panel svg { width: 100%; height: auto; display: block; }
80
+ .legend { display: flex; flex-wrap: wrap; gap: 14px; font-size: 13px; color: var(--muted); margin: 8px 0 0; }
81
+ .legend span::before { content: ""; display: inline-block; width: 10px; height: 10px; border-radius: 2px; margin-right: 6px; vertical-align: -1px; background: var(--c); }
82
+ .findings { display: grid; gap: 14px; counter-reset: f; padding: 0; list-style: none; }
83
+ .findings li { display: grid; grid-template-columns: 2.2em 1fr; gap: 6px; margin: 0; }
84
+ .findings li::before { counter-increment: f; content: counter(f); font-family: var(--f-mono); color: var(--hema); font-weight: 500; }
85
+ .findings b { font-weight: 700; }
86
+
87
+ .flow { background: var(--surface); border-radius: 8px; padding: 16px; margin: 12px 0 16px; display: grid; gap: 10px; overflow-x: auto; }
88
+ .flow .row { display: grid; grid-template-columns: 7.5em 1.2em minmax(11em, 1.4fr) 1.2em minmax(9em, 1fr) 1.2em 9em; align-items: center; min-width: 640px; }
89
+ .flow .b { border: 1px solid var(--rule); background: var(--bg); border-radius: 6px; padding: 6px 9px; font-size: 13px; line-height: 1.45; text-align: center; }
90
+ .flow .b small { display: block; color: var(--muted); font-size: 11.5px; }
91
+ .flow .in { font-weight: 500; }
92
+ .flow .he .b { border-color: var(--hema); }
93
+ .flow .z { border-color: var(--hema); color: var(--hema); font-weight: 700; }
94
+ .flow .ar { text-align: center; color: var(--muted); font-family: var(--f-mono); }
95
+ pre.mermaid { background: var(--surface); border-radius: 8px; padding: 16px; overflow-x: auto; margin: 12px 0 16px; text-align: center; }
96
+ .toc { display: flex; flex-wrap: wrap; gap: 6px 16px; font-size: 13px; margin-top: 4px; }
97
+ .toc a { text-decoration: none; color: var(--muted); }
98
+ .toc a:hover, .toc a:focus-visible { color: var(--hema); text-decoration: underline; }
99
+ a:focus-visible { outline: 2px solid var(--hema); outline-offset: 2px; }
100
+ @media (max-width: 560px) {
101
+ h1 { font-size: 28px; } h2 { font-size: 23px; }
102
+ th, td { padding: 6px 7px; }
103
+ }
104
+ </style>
105
+ </head>
106
+ <body>
107
+ <div class="wrap">
108
+ <header>
109
+ <div class="eyebrow">ImageBind-style · H&amp;E / mIF / RNA / text · 最终结果与独立复现 · 2026-10-30</div>
110
+ <h1>四模态病理嵌入模型</h1>
111
+ <p class="lede col">把 H&amp;E 图像、多重免疫荧光(mIF,蛋白)、空间转录组(RNA)和病理文本放进同一个 1536 维空间。
112
+ 锚点是冻结的 UNI2-h 图像空间;所有模态只用真实配对数据训练,虚拟和合成数据只用于评估。
113
+ 最终模型(EJ-ad+MV,3 种子适配器平均)已训练完成,并提供从原始输入直接生成嵌入的接口 <code>embed.py</code>。
114
+ 2026-10-29 又在独立 A800 环境中完成了发布模型评估、fold 0 重训、5 折重训和 release 重训,全部复现检查通过。</p>
115
+ <nav class="toc" aria-label="目录">
116
+ <a href="#setup">设定与数据</a><a href="#model">最终模型</a><a href="#results">结果</a><a href="#reproduction">独立复现</a><a href="#findings">主要发现</a>
117
+ <a href="#encoders">编码器选择</a><a href="#virtual">虚拟模态</a><a href="#limits">局限</a><a href="#usage">使用方法</a><a href="#files">文件</a>
118
+ </nav>
119
+ </header>
120
+
121
+ <section id="setup">
122
+ <h2>设定与数据</h2>
123
+ <div class="col">
124
+ <p>没有任何数据集同时测量四种模态,所以采用 ImageBind 的思路:每个模态只和 H&amp;E 配对训练,H&amp;E 以外的模态两两之间的对齐是“涌现”出来的。</p>
125
+ <ul>
126
+ <li><b>训练配对只用真实数据:</b>ORION 结直肠癌(H&amp;E–mIF)、HEST-1k Visium(H&amp;E–RNA)、TCGA/PathGen(H&amp;E–文本)。</li>
127
+ <li><b>划分:</b>按病人(HEST 按研究|病人组)分成 train/val/test,5 折交叉验证;val 只用于早停,所有数字都是 test 上的。</li>
128
+ <li><b>虚拟和合成数据只用于测试:</b>STPath 虚拟 RNA、MIPHEI 虚拟 mIF、GPT 合成描述。它们只用来给“没有真实配对”的模态对构建测试集。</li>
129
+ <li><b>指标:</b>100 个样本的检索库里的 R@1(双向平均,随机水平 0.01),抽 50 次取平均;配对准确率是同一 100 库里的一对一匈牙利匹配(随机水平 0.01)。</li>
130
+ </ul>
131
+ </div>
132
+ <div class="tbl">
133
+ <table>
134
+ <thead><tr><th>数据集</th><th>配对</th><th>规模</th><th>用途</th></tr></thead>
135
+ <tbody>
136
+ <tr><td>ORION CRC</td><td>H&amp;E – mIF(16 个标记)</td><td class="mono">3,187 图块 · 约 40 名病人</td><td>训练 + 测试</td></tr>
137
+ <tr><td>HEST-1k Visium</td><td>H&amp;E – RNA(14,802 基因)</td><td class="mono">9,484 spots · 57 项研究 · 16 器官</td><td>训练 + 测试</td></tr>
138
+ <tr><td>TCGA / PathGen-1.6M</td><td>H&amp;E – 文本</td><td class="mono">6,144 图像 · 6,115 条清洗后文本</td><td>训练 + 测试</td></tr>
139
+ <tr><td>STPath / MIPHEI / GPT 描述</td><td>虚拟 RNA、虚拟 mIF、合成文本</td><td class="mono">ORION、TCGA 测试图块</td><td>只用于测试</td></tr>
140
+ <tr><td>DLPFC(spatialLIBD)</td><td>H&amp;E – RNA(脑)</td><td class="mono">482 spots · 3 名供体</td><td>外部测试</td></tr>
141
+ </tbody>
142
+ </table>
143
+ </div>
144
+ </section>
145
+
146
+ <section id="model">
147
+ <h2>最终模型</h2>
148
+ <div class="col">
149
+ <p>两阶段训练。第一阶段给每个编码器单独训练一个映射头,映射到冻结的 UNI2 空间。第二阶段冻结所有映射头,只训练一个 H&amp;E 残差适配器,它同时读 UNI2 和 MedVTok 的特征。</p>
150
+ </div>
151
+ <div class="flow" role="img" aria-label="模型结构:四种模态各自经编码器和映射头进入 1536 维共享空间">
152
+ <div class="row he"><div class="b in">H&amp;E 图像</div><div class="ar">→</div><div class="b">UNI2-h(冻结)<br>+ MedVTok(冻结)</div><div class="ar">→</div><div class="b">UNI2 + 残差适配器<small>3 个种子取平均</small></div><div class="ar">→</div><div class="b z">1536 维共享空间</div></div>
153
+ <div class="row "><div class="b in">mIF 图块</div><div class="ar">→</div><div class="b">VirTues<small>16 个标志物</small></div><div class="ar">→</div><div class="b">MLP 头</div><div class="ar">→</div><div class="b z">1536 维共享空间</div></div>
154
+ <div class="row "><div class="b in">RNA 计数</div><div class="ar">→</div><div class="b">hvg · Tahoe-x1<br>SE-600M · AIDO.Cell</div><div class="ar">→</div><div class="b">4 个线性头<small>后期融合</small></div><div class="ar">→</div><div class="b z">1536 维共享空间</div></div>
155
+ <div class="row "><div class="b in">文本</div><div class="ar">→</div><div class="b">KEEP · BiomedCLIP<br>Qwen3-Emb-0.6B</div><div class="ar">→</div><div class="b">3 个线性头<small>后期融合</small></div><div class="ar">→</div><div class="b z">1536 维共享空间</div></div>
156
+ </div>
157
+ <div class="col">
158
+ <ul>
159
+ <li><b>第一阶段:</b>每个映射头用 InfoNCE 对齐冻结的 UNI2(文本是多正样本 InfoNCE,同一图像的多条文本都算正样本)。RNA 和文本是后期融合:<code>z = normalise(Σ normalise(head_e(x_e)))</code>。</li>
160
+ <li><b>第二阶段:</b>只训练 H&amp;E 适配器和温度参数:<code>H&amp;E = UNI2 + mean_s A_s([UNI2, c·MedVTok])</code>。损失是三种配对损失之和加上对 UNI2 相似度结构的蒸馏(λ=1),学习率 1e-4,1000 步,按验证集三种 R@1 的几何平均早停。用 3 个随机种子各训练一个适配器,取平均。</li>
161
+ <li><b>后果:</b>mIF、RNA、文本的嵌入和第一阶段完全一样,所以涌现配对不受第二阶段影响;只有 H&amp;E 这一侧变好。</li>
162
+ <li><b>发布版:</b><code>models/ej_ad_mv/</code>,用 fold 0 的 train + test 训练(ORION 3,000 图块、HEST 8,938 spots、TCGA 5,615 条文本),fold 0 的 val 用于早停。它没有自己的测试集,预期性能就是下面的 5 折交叉验证结果。</li>
163
+ </ul>
164
+ </div>
165
+ </section>
166
+
167
+ <section id="results">
168
+ <h2>结果</h2>
169
+ <h3>最终模型,5 折测试集</h3>
170
+ <div class="tbl">
171
+ <table>
172
+ <thead><tr><th>配对</th><th>类型</th><th>数据集</th><th class="n">R@1</th><th class="n">R@10</th><th class="n">配对准确率</th></tr></thead>
173
+ <tbody>
174
+ <tr><td>H&amp;E ↔ mIF</td><td><span class="kind trained">训练</span></td><td>ORION</td><td class="n">0.801 ± 0.043</td><td class="n">0.991</td><td class="n">0.942</td></tr>
175
+ <tr><td>H&amp;E ↔ RNA</td><td><span class="kind trained">训练</span></td><td>HEST</td><td class="n">0.203 ± 0.033</td><td class="n">0.625</td><td class="n">0.258</td></tr>
176
+ <tr><td>H&amp;E ↔ 文本</td><td><span class="kind trained">训练</span></td><td>TCGA</td><td class="n">0.323 ± 0.007</td><td class="n">0.813</td><td class="n">0.347</td></tr>
177
+ <tr><td>mIF ↔ RNA(虚拟)</td><td><span class="kind emergent">涌现</span></td><td>ORION</td><td class="n">0.141 ± 0.007</td><td class="n">0.657</td><td class="n">0.194</td></tr>
178
+ <tr><td>mIF ↔ 文本(合成)</td><td><span class="kind emergent">涌现</span></td><td>ORION</td><td class="n">0.089 ± 0.008</td><td class="n">0.491</td><td class="n">0.104</td></tr>
179
+ <tr><td>文本 ↔ RNA(虚拟)</td><td><span class="kind emergent">涌现</span></td><td>TCGA</td><td class="n">0.095 ± 0.006</td><td class="n">0.436</td><td class="n">0.100</td></tr>
180
+ <tr><td>文本 ↔ mIF(MIPHEI 虚拟)</td><td><span class="kind emergent">涌现</span></td><td>TCGA</td><td class="n">0.046 ± 0.005</td><td class="n">0.271</td><td class="n">0.051</td></tr>
181
+ <tr><td>H&amp;E ↔ RNA</td><td><span class="kind virtual">外部</span></td><td>DLPFC(脑)</td><td class="n">0.012</td><td class="n">0.112</td><td class="n">0.012</td></tr>
182
+ </tbody>
183
+ </table>
184
+ </div>
185
+ <p class="note col">随机水平:R@1 0.01,R@10 0.10,配对准确率 0.01。涌现配对的一侧是虚拟或合成数据,这些数据本身有误差,所以数值偏保守。DLPFC 是第一阶段(E)的结果;第二阶段不改变 RNA ���。</p>
186
+
187
+ <h3>各阶段的提升(训练配对 R@1,5 折均值)</h3>
188
+ <div class="panels" id="chart"></div>
189
+ <div class="legend" aria-hidden="true">
190
+ <span style="--c: var(--steel)">单编码器(S4)</span>
191
+ <span style="--c: var(--eosin)">多编码器融合(E)</span>
192
+ <span style="--c: color-mix(in srgb, var(--hema) 55%, var(--bg))">+ H&amp;E 适配器 / + MedVTok</span>
193
+ <span style="--c: var(--hema)">最终(3 种子平均)</span>
194
+ </div>
195
+
196
+ <h3>涌现配对(R@1)</h3>
197
+ <div class="tbl">
198
+ <table>
199
+ <thead><tr><th>阶段</th><th class="n">mIF↔RNA(虚拟)</th><th class="n">mIF↔文本(合成)</th><th class="n">文本↔RNA(虚拟)</th><th class="n">文本↔mIF(虚拟)</th></tr></thead>
200
+ <tbody>
201
+ <tr><td>单编码器,单独训练(S4)</td><td class="n">0.122</td><td class="n">0.076</td><td class="n">0.069</td><td class="n">0.038</td></tr>
202
+ <tr><td>单编码器,联合微调所有头(J8)</td><td class="n">0.122</td><td class="n">0.073</td><td class="n">0.065</td><td class="n">0.035</td></tr>
203
+ <tr><td>多编码器融合(E)</td><td class="n">0.141</td><td class="n">0.089</td><td class="n">0.095</td><td class="n">0.046</td></tr>
204
+ <tr><td>融合 + 联合微调 mIF 头(EJ-frz)</td><td class="n">0.134</td><td class="n">0.087</td><td class="n">0.095</td><td class="n">0.042</td></tr>
205
+ <tr class="final"><td>最终:只训练 H&amp;E 适配器</td><td class="n">0.141</td><td class="n">0.089</td><td class="n">0.095</td><td class="n">0.046</td></tr>
206
+ </tbody>
207
+ </table>
208
+ </div>
209
+ </section>
210
+
211
+ <section id="reproduction">
212
+ <h2>独立复现:发布结果可重现</h2>
213
+ <div class="col">
214
+ <p><strong>总体结论:</strong>在 cuipeng 服务器的一张 NVIDIA A800-SXM4-80GB 上,从发布的编码器特征重新执行完整的 <code>reproduce.sh</code>。流程包括评估已发布 fold-0 checkpoint、重训 fold 0、重训 5 折、逐项比较发布结果,以及用 fold-0 train + test 重训 release 模型。任务最终状态为 <strong class="ok">Success</strong>,日志给出 <code>REPRODUCED within tolerance</code> 和 <code>FOURMODAL_REPRODUCTION_COMPLETE</code>。</p>
215
+ <ul>
216
+ <li><b>环境:</b>Python 3.12.1、PyTorch 2.7.1+cu128、CUDA 12.8、NumPy 2.4.6、Pandas 2.3.3、SciPy 1.16.3。</li>
217
+ <li><b>数据检查:</b>26 个特征数组,共 0.933 GiB;全部可读取、非空且无 NaN/Inf;三组数据的 5 折划分完整。</li>
218
+ <li><b>发布模型检查:</b>重新评估发布 fold-0 模型,7 个模态对与随模型发布的 <code>test.csv</code> 最大 R@1 差异为 0.0001。</li>
219
+ </ul>
220
+ </div>
221
+
222
+ <h3>fold 0 重训:留出测试集</h3>
223
+ <div class="tbl">
224
+ <table>
225
+ <thead><tr><th>模态对</th><th class="n">本次重训 R@1</th><th class="n">发布 R@1</th><th class="n">绝对差异</th><th>复现检查</th></tr></thead>
226
+ <tbody>
227
+ <tr><td>H&amp;E ↔ mIF(ORION)</td><td class="n">0.7608</td><td class="n">0.7834</td><td class="n">0.0226</td><td class="ok">通过</td></tr>
228
+ <tr><td>H&amp;E ↔ RNA(HEST)</td><td class="n">0.1853</td><td class="n">0.1917</td><td class="n">0.0064</td><td class="ok">通过</td></tr>
229
+ <tr><td>H&amp;E ↔ 文本(TCGA)</td><td class="n">0.3240</td><td class="n">0.3203</td><td class="n">0.0037</td><td class="ok">通过</td></tr>
230
+ <tr><td>mIF ↔ RNA(虚拟,ORION)</td><td class="n">0.1358</td><td class="n">0.1352</td><td class="n">0.0006</td><td class="ok">通过</td></tr>
231
+ <tr><td>mIF ↔ 文本(合成,ORION)</td><td class="n">0.0978</td><td class="n">0.0987</td><td class="n">0.0009</td><td class="ok">通过</td></tr>
232
+ <tr><td>文本 ↔ RNA(虚拟,TCGA)</td><td class="n">0.0999</td><td class="n">0.1000</td><td class="n">0.0001</td><td class="ok">通过</td></tr>
233
+ <tr><td>文本 ↔ mIF(MIPHEI,TCGA)</td><td class="n">0.0484</td><td class="n">0.0491</td><td class="n">0.0007</td><td class="ok">通过</td></tr>
234
+ </tbody>
235
+ </table>
236
+ </div>
237
+
238
+ <h3>5 折重训:最终 <code>ens-es</code> 规则</h3>
239
+ <div class="tbl">
240
+ <table>
241
+ <thead><tr><th>模态对</th><th class="n">本次 5 折 R@1</th><th class="n">发布 R@1</th><th class="n">绝对差异</th><th>复现检查</th></tr></thead>
242
+ <tbody>
243
+ <tr><td>H&amp;E ↔ mIF(ORION)</td><td class="n">0.7967</td><td class="n">0.8010</td><td class="n">0.0042</td><td class="ok">通过</td></tr>
244
+ <tr><td>H&amp;E ↔ RNA(HEST)</td><td class="n">0.2021</td><td class="n">0.2030</td><td class="n">0.0009</td><td class="ok">通过</td></tr>
245
+ <tr><td>H&amp;E ↔ 文本(TCGA)</td><td class="n">0.3231</td><td class="n">0.3232</td><td class="n">0.0001</td><td class="ok">通过</td></tr>
246
+ <tr><td>mIF ↔ RNA(虚拟,ORION)</td><td class="n">0.1414</td><td class="n">0.1414</td><td class="n">0.0000</td><td class="ok">通过</td></tr>
247
+ <tr><td>mIF ↔ 文本(合成,ORION)</td><td class="n">0.0885</td><td class="n">0.0887</td><td class="n">0.0001</td><td class="ok">通过</td></tr>
248
+ <tr><td>文本 ↔ RNA(虚拟,TCGA)</td><td class="n">0.0966</td><td class="n">0.0953</td><td class="n">0.0013</td><td class="ok">通过</td></tr>
249
+ <tr><td>文本 ↔ mIF(MIPHEI,TCGA)</td><td class="n">0.0464</td><td class="n">0.0465</td><td class="n">0.0001</td><td class="ok">通过</td></tr>
250
+ </tbody>
251
+ </table>
252
+ </div>
253
+ <p class="note col">所有 fold-0 和 5 折对比均落在发布代码预定义的容差内。最终还生成并独立加载验证了 <code>models/repro_fold0/model.pt</code>、<code>models/repro_release/model.pt</code> 和三张 <code>final_cv_*_repro.csv</code>。本次执行的是特征级复现;没有执行可选的 <code>RAW=1</code> 原始输入编码器检查。</p>
254
+ </section>
255
+
256
+ <section id="findings">
257
+ <h2>主要发现</h2>
258
+ <ol class="findings col">
259
+ <li><div><b>UNI2-h 是最好的冻结锚点。</b>在 mIF、RNA、文本三种训练配对上都没有被显著超过;GigaPath 接近(RNA 差 0.035),CONCH 在 H&amp;E↔mIF 上低 0.155。MedVTok 当锚点也更差(H&amp;E↔RNA 0.131 对 0.192)。</div></li>
260
+ <li><div><b>多编码器后期融合是最大的单项提升。</b>RNA 用 4 个编码器、文本用 3 个,H&amp;E↔RNA +0.037、H&amp;E↔文本 +0.062,4 个涌现配对也全部提升(5/5 折)。拼接(早期融合)和同一编码器多种子平均都达不到这个效果,说明这些编码器是互补的。</div></li>
261
+ <li><div><b>联合训练要只动 H&amp;E 一侧。</b>从头训练共享的 H&amp;E 头会让 H&amp;E↔mIF 变好,但涌现配对损失 26–74%。冻结所有模态头、只训练零初始化的残差适配器,H&amp;E↔mIF +0.10,涌现配对完全不变。</div></li>
262
+ <li><div><b>MedVTok 作为适配器的额外输入有效,作为锚点无效。</b>额外输入使 H&amp;E↔mIF +0.015、H&amp;E↔文本 +0.016。换成同尺寸的 UNI2 随机投影就没有提升,说明增益来自 MedVTok 的信息而不是参数量。</div></li>
263
+ <li><div><b>第二阶段的早停不稳定,3 个种子平均解决了这个问题。</b>验证曲线在 100 步后基本是平的,单次早停选中的步数在 100–900 之间波动,同一设置重跑 H&amp;E↔mIF 可以差 0.05。3 个早停适配器取平均后,H&amp;E↔文本比单种子再 +0.015(5/5 折,p=0.02),也是三种规则里几何平均最高的。</div></li>
264
+ <li><div><b>线性头比 MLP 头更适合 RNA 和文本。</b>训练配对持平,涌现配对 +5%;mIF 保留 MLP 头。</div></li>
265
+ <li><div><b>用虚拟配对直接训练不如走锚点的涌现路线。</b>文本↔蛋白在真实 mIF 上 0.596 对 0.678(AUROC)。所以虚拟数据只用作测试,从不进入训练。</div></li>
266
+ <li><div><b>实例级的涌现对齐仍然弱。</b>mIF↔RNA 0.141 是随机水平的 14 倍,但比训练配对低一个数量级;概念级对齐(AUROC 0.6–0.7)更可靠。</div></li>
267
+ </ol>
268
+ </section>
269
+
270
+ <section id="encoders">
271
+ <h2>编码器选择</h2>
272
+ <div class="tbl">
273
+ <table>
274
+ <thead><tr><th>模态</th><th>最终使用</th><th>依据(5 折配对检验)</th></tr></thead>
275
+ <tbody>
276
+ <tr><td>H&amp;E</td><td>UNI2-h + MedVTok(只进适配器)</td><td>UNI2 在所有训练配对上不被显著超过;MedVTok 额外输入 mIF +0.015、文本 +0.016</td></tr>
277
+ <tr><td>mIF</td><td>VirTues(16 标记)+ MLP 头</td><td>从头训练的 ConvNeXt-T 在 H&amp;E↔mIF 上高 0.03,但 VirTues 的跨模态迁移好得多(mIF↔markers 0.66 对 0.48),且不绑定固定标记面板</td></tr>
278
+ <tr><td>RNA</td><td>hvg + Tahoe-x1 + SE-600M + AIDO.Cell,各一个线性头</td><td>单个基础模型最多 +0.016;4 个融合 +0.037,接近 10 个融合(+0.044)</td></tr>
279
+ <tr><td>文本</td><td>KEEP + BiomedCLIP + Qwen3-Emb-0.6B,各一个线性头</td><td>KEEP 单个最好(0.278);3 个融合 0.299,接近 5 个融合(0.303)</td></tr>
280
+ </tbody>
281
+ </table>
282
+ </div>
283
+ </section>
284
+
285
+ <section id="virtual">
286
+ <h2>虚拟模态(只用于评估)</h2>
287
+ <div class="col">
288
+ <p>每种虚拟模态先做校准:在有真实数据的同一批样本上,用虚拟数据替换真实数据,看配对结果是否接近。</p>
289
+ </div>
290
+ <div class="tbl">
291
+ <table>
292
+ <thead><tr><th>虚拟模态</th><th>校准(真实 → 虚拟,同一批样本)</th><th>结论</th></tr></thead>
293
+ <tbody>
294
+ <tr><td>STPath 虚拟 RNA</td><td>HEST H&amp;E↔RNA 0.148 → 0.126;STPath 未见过的样本 0.086 → 0.080</td><td class="ok">可用</td></tr>
295
+ <tr><td>GPT 合成描述</td><td>TCGA H&amp;E↔文本 0.219 → 0.162(约 0.75 倍)</td><td class="ok">可用,偏保守</td></tr>
296
+ <tr><td>MIPHEI 虚拟 mIF</td><td>ORION 未见过的测试图块:配对准确率 0.92 → 0.55(约 0.6 倍)</td><td class="ok">可用</td></tr>
297
+ <tr><td>GigaTIME 虚拟 mIF</td><td>ORION H&amp;E↔mIF 0.644 → 0.038</td><td class="bad">不可用,已弃用</td></tr>
298
+ </tbody>
299
+ </table>
300
+ </div>
301
+ </section>
302
+
303
+ <section id="limits">
304
+ <h2>局限</h2>
305
+ <ul class="col">
306
+ <li><b>外部泛化差:</b>脑组织 DLPFC 上所有非循环配对都在随机水平(H&amp;E↔RNA 0.012)。训练集 HEST 里脑组织也只有 0.021。模型目前适用于训练数据覆盖的组织类型。</li>
307
+ <li><b>H&amp;E↔文本的 MedVTok 增益可能偏高:</b>MedVTok 的预训练图像包含 PathGen 1.6M,见过我们的 TCGA 测试图像(只有图像,没有文本)。ORION 上的 mIF 增益不受影响。</li>
308
+ <li><b>验证集小:</b>ORION 每折只有 187–276 个验证图块,所以第二阶段用了 3 种子平均来降低早停的随机性。</li>
309
+ <li><b>涌现配对的测试数据一侧是虚拟或合成的,</b>数值是保守估计,不是真实数据上的精确值。</li>
310
+ <li><b>新数据的 RNA 批次效应:</b>默认用 HEST 训练集的统计量做标准化;新平台或新实验室的数据建议用 <code>zscore="self"</code>(外部测试就是这样做的)。</li>
311
+ </ul>
312
+ </section>
313
+
314
+ <section id="usage">
315
+ <h2>使用方法</h2>
316
+ <div class="col">
317
+ <p>运行环境:<code>.venv/bin/python -I</code>,需要 GPU。所有输出都是 L2 归一化的 (N, 1536) 向量,相似度就是点积。</p>
318
+ </div>
319
+ <pre class="code">from embed import Embedder
320
+ E = Embedder("models/ej_ad_mv") # 发布版模型
321
+
322
+ z_he = E.he(images) # H&amp;E 图块:PIL 图像或 (N,H,W,3) uint8;约 0.5 µm/px,112–166 µm 视野
323
+ z_txt = E.text(["Tumor cells with ...", ...])
324
+ z_rna = E.rna(counts, genes, zscore="train") # 原始计数(spots × 基因)+ HGNC 基因名;新数据集可用 zscore="self"
325
+ z_mif = E.mif(tiles, slide) # (N,16,H,W) mIF 图块,通道顺序 = embed.MIF_MARKERS,8 位强度;附每个图块的切片 ID
326
+
327
+ sim = z_he @ z_rna.T # 跨模态相似度
328
+ # 已有特征时:E.he_from_feats(uni2, medvtok)、E.mif_from_feats(virtues)、E.rna_from_feats({...})、E.text_from_feats({...})</pre>
329
+
330
+ <h3>接口验证(<code>53_embed_check.py</code>)</h3>
331
+ <div class="col"><p>从原始像素、字符串和计数矩阵出发,用 <code>embed.py</code> 重新计算特征,和训练时缓存的特征逐项比较;再用 fold 0 模型在留出测试集上做端到端检索。</p></div>
332
+ <div class="tbl">
333
+ <table>
334
+ <thead><tr><th>检查</th><th>结果</th></tr></thead>
335
+ <tbody>
336
+ <tr><td>UNI2-h、MedVTok(ORION、PathGen、HEST 图像)</td><td class="mono">余弦中位数 1.0000,最低 ≥ 0.9997</td></tr>
337
+ <tr><td>KEEP、BiomedCLIP、Qwen3(TCGA 文本)</td><td class="mono">中位数 1.0000 / 1.0000 / 0.9998(BiomedCLIP 个别 0.93,bf16 批次差异)</td></tr>
338
+ <tr><td>hvg、AIDO.Cell / Tahoe-x1、SE-600M(HEST)</td><td class="mono">1.0000 / 0.991、0.994(后两者按官方做法随机采样基因)</td></tr>
339
+ <tr><td>VirTues(全部 3,187 个 ORION 图块)</td><td class="mono">中位数 1.0000,最低 1.0000</td></tr>
340
+ <tr><td>端到端 R@1:原始输入 vs 缓存特征</td><td class="mono">mIF 0.792 / 0.792 · RNA 0.194 / 0.194 · 文本 0.335 / 0.336</td></tr>
341
+ </tbody>
342
+ </table>
343
+ </div>
344
+
345
+ </section>
346
+
347
+ <section id="files">
348
+ <h2>文件</h2>
349
+ <div class="tbl">
350
+ <table>
351
+ <thead><tr><th>路径</th><th>内容</th></tr></thead>
352
+ <tbody>
353
+ <tr><td><code>embed.py</code></td><td>推理接口(Embedder、Bind4)</td></tr>
354
+ <tr><td><code>52_final_model.py</code></td><td>最终模型训练:<code>cv</code>(选择规则)、<code>fold0</code>、<code>release</code></td></tr>
355
+ <tr><td><code>53_embed_check.py</code></td><td>原始输入验证,结果在 <code>results/embed_check.csv</code></td></tr>
356
+ <tr><td><code>models/ej_ad_mv/</code></td><td>发布版模型:<code>model.pt</code>(77 MB,含标准化统计量)、<code>meta.json</code>、验证曲线</td></tr>
357
+ <tr><td><code>models/ej_ad_mv_fold0/</code></td><td>fold 0 模型及其留出测试结果 <code>test.csv</code></td></tr>
358
+ <tr><td><code>results/final_cv_*.csv</code></td><td>5 折 × 3 种子的选择规则实验</td></tr>
359
+ <tr><td><code>RESULTS.md</code></td><td>全部实验的完整记录(01_–53_)</td></tr>
360
+ </tbody>
361
+ </table>
362
+ </div>
363
+ </section>
364
+ </div>
365
+
366
+ <script>
367
+ (function () {
368
+ // Trained-pair R@1, 5-fold means (RESULTS.md: 48_ S4 / E, 51_ EJ-ad / EJ-ad+MV, 52_ cv ens-es)
369
+ var stages = ["单编码器 S4", "多编码器融合 E", "+ H&E 适配器", "+ MedVTok", "最终(3 种子)"];
370
+ var colors = ["var(--steel)", "var(--eosin)", "color-mix(in srgb, var(--hema) 55%, var(--bg))",
371
+ "color-mix(in srgb, var(--hema) 55%, var(--bg))", "var(--hema)"];
372
+ var pairs = [
373
+ { name: "H&E ↔ mIF(ORION)", max: 1.0, ticks: [0, 0.25, 0.5, 0.75, 1.0], v: [0.675, 0.675, 0.776, 0.792, 0.801] },
374
+ { name: "H&E ↔ RNA(HEST)", max: 0.25, ticks: [0, 0.05, 0.1, 0.15, 0.2, 0.25], v: [0.155, 0.192, 0.201, 0.200, 0.203] },
375
+ { name: "H&E ↔ 文本(TCGA)", max: 0.35, ticks: [0, 0.1, 0.2, 0.3], v: [0.236, 0.299, 0.299, 0.315, 0.323] }
376
+ ];
377
+ var NS = "http://www.w3.org/2000/svg";
378
+ var W = 320, labelW = 104, valW = 40, rowH = 26, top = 6, axisH = 22;
379
+ var plotW = W - labelW - valW;
380
+ var H = top + stages.length * rowH + axisH;
381
+ function el(n, a, t) { var e = document.createElementNS(NS, n); for (var k in a) e.setAttribute(k, a[k]); if (t != null) e.textContent = t; return e; }
382
+ var host = document.getElementById("chart");
383
+ pairs.forEach(function (p) {
384
+ var div = document.createElement("div"); div.className = "panel";
385
+ var h = document.createElement("h4"); h.textContent = p.name; div.appendChild(h);
386
+ var svg = el("svg", { viewBox: "0 0 " + W + " " + H, role: "img", "aria-label": p.name + " R@1: " + stages.map(function (s, i) { return s + " " + p.v[i].toFixed(3); }).join(",") });
387
+ var x = function (v) { return labelW + v / p.max * plotW; };
388
+ p.ticks.forEach(function (t) {
389
+ svg.appendChild(el("line", { x1: x(t), x2: x(t), y1: top, y2: top + stages.length * rowH, stroke: "var(--rule)", "stroke-width": 1 }));
390
+ svg.appendChild(el("text", { x: x(t), y: H - 6, "text-anchor": "middle", "font-size": 10, fill: "var(--muted)", "font-family": "var(--f-mono)" }, t === 0 ? "0" : String(t)));
391
+ });
392
+ stages.forEach(function (s, i) {
393
+ var y = top + i * rowH;
394
+ svg.appendChild(el("text", { x: labelW - 8, y: y + rowH / 2 + 4, "text-anchor": "end", "font-size": 11, fill: "var(--fg)" }, s));
395
+ svg.appendChild(el("rect", { x: labelW, y: y + 5, width: x(p.v[i]) - labelW, height: rowH - 10, rx: 2, fill: colors[i] }));
396
+ svg.appendChild(el("text", { x: x(p.v[i]) + 5, y: y + rowH / 2 + 4, "font-size": 11, fill: i === stages.length - 1 ? "var(--hema)" : "var(--muted)", "font-family": "var(--f-mono)", "font-weight": i === stages.length - 1 ? 600 : 400 }, p.v[i].toFixed(3)));
397
+ });
398
+ div.appendChild(svg); host.appendChild(div);
399
+ });
400
+ })();
401
+ </script>
402
+
403
+ </body>
404
  </html>
previous_report.html ADDED
@@ -0,0 +1,308 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <!doctype html>
2
+ <html lang="zh-CN">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1">
6
+ <title>四模态病理对齐实验报告</title>
7
+ <meta name="description" content="H&E / 文本 / mIF 蛋白 / RNA 四模态 ImageBind 式对齐:最终协议结果、虚拟数据校准、外部测试与最佳训练方案">
8
+ <style>
9
+ :root{
10
+ --bg:#f7f6f2; --panel:#ffffff; --ink:#1d1f23; --muted:#5d636e; --line:#e3e1da;
11
+ --accent:#2f6f5e; --accent-soft:#e2efe9; --warn:#a4561b; --warn-soft:#f8eadf;
12
+ --bad:#a33a3a; --bad-soft:#f6e2e2; --bar:#2f6f5e; --bar2:#c9a24a; --chance:#a33a3a;
13
+ }
14
+ @media (prefers-color-scheme: dark){
15
+ :root:not([data-theme="light"]){
16
+ --bg:#15171a; --panel:#1d2024; --ink:#e8e6e1; --muted:#9aa0a9; --line:#30343a;
17
+ --accent:#6fc2a6; --accent-soft:#1f3530; --warn:#e2a06a; --warn-soft:#3a2b20;
18
+ --bad:#e38787; --bad-soft:#3a2323; --bar:#6fc2a6; --bar2:#d9b862; --chance:#e38787;
19
+ }
20
+ }
21
+ :root[data-theme="dark"]{
22
+ --bg:#15171a; --panel:#1d2024; --ink:#e8e6e1; --muted:#9aa0a9; --line:#30343a;
23
+ --accent:#6fc2a6; --accent-soft:#1f3530; --warn:#e2a06a; --warn-soft:#3a2b20;
24
+ --bad:#e38787; --bad-soft:#3a2323; --bar:#6fc2a6; --bar2:#d9b862; --chance:#e38787;
25
+ }
26
+ *{box-sizing:border-box}
27
+ body{margin:0;background:var(--bg);color:var(--ink);font:15px/1.65 -apple-system,BlinkMacSystemFont,"Segoe UI","PingFang SC","Hiragino Sans GB","Microsoft YaHei","Noto Sans CJK SC",sans-serif}
28
+ .wrap{max-width:1040px;margin:0 auto;padding:32px 16px 64px}
29
+ header h1{font-size:28px;line-height:1.3;margin:0 0 6px}
30
+ header p.sub{color:var(--muted);margin:0 0 18px}
31
+ nav{display:flex;flex-wrap:wrap;gap:6px 14px;font-size:13.5px;margin:0 0 26px;padding:10px 14px;background:var(--panel);border:1px solid var(--line);border-radius:10px}
32
+ nav a{color:var(--accent);text-decoration:none}
33
+ nav a:hover{text-decoration:underline}
34
+ h2{font-size:21px;margin:38px 0 10px;padding-top:8px;border-top:1px solid var(--line)}
35
+ h3{font-size:16.5px;margin:22px 0 8px}
36
+ p{margin:8px 0}
37
+ .card{background:var(--panel);border:1px solid var(--line);border-radius:12px;padding:16px 18px;margin:12px 0}
38
+ .verdict{border-left:5px solid var(--accent);background:var(--accent-soft)}
39
+ .kpis{display:grid;grid-template-columns:repeat(auto-fit,minmax(200px,1fr));gap:10px;margin:14px 0}
40
+ .kpi{background:var(--panel);border:1px solid var(--line);border-radius:12px;padding:12px 14px}
41
+ .kpi .v{font-size:26px;font-weight:700;color:var(--accent);line-height:1.2}
42
+ .kpi .l{font-size:13px;color:var(--muted)}
43
+ .tbl{overflow-x:auto;margin:10px 0;border:1px solid var(--line);border-radius:10px;background:var(--panel)}
44
+ table{border-collapse:collapse;width:100%;font-size:13.8px}
45
+ th,td{padding:7px 10px;border-bottom:1px solid var(--line);text-align:left;vertical-align:top;white-space:nowrap}
46
+ td.wrap,th.wrap{white-space:normal;min-width:180px}
47
+ th{background:var(--bg);font-weight:600}
48
+ tr:last-child td{border-bottom:none}
49
+ td.n{text-align:right;font-variant-numeric:tabular-nums}
50
+ .tag{display:inline-block;font-size:12px;padding:1px 7px;border-radius:999px;margin-left:4px}
51
+ .ok{background:var(--accent-soft);color:var(--accent)}
52
+ .warn{background:var(--warn-soft);color:var(--warn)}
53
+ .bad{background:var(--bad-soft);color:var(--bad)}
54
+ .muted{color:var(--muted)}
55
+ .small{font-size:13px}
56
+ ul{margin:6px 0 6px 20px;padding:0}
57
+ li{margin:3px 0}
58
+ .bars{margin:8px 0}
59
+ .bar{display:grid;grid-template-columns:minmax(120px,240px) 1fr 56px;align-items:center;gap:10px;margin:5px 0;font-size:13.5px}
60
+ .track{position:relative;height:16px;background:var(--bg);border:1px solid var(--line);border-radius:4px}
61
+ .fill{position:absolute;left:0;top:0;bottom:0;background:var(--bar);border-radius:3px}
62
+ .fill.b2{background:var(--bar2)}
63
+ .chance{position:absolute;top:-3px;bottom:-3px;width:2px;background:var(--chance)}
64
+ .bar .val{text-align:right;font-variant-numeric:tabular-nums}
65
+ .legend{font-size:12.5px;color:var(--muted)}
66
+ .recipe{counter-reset:s}
67
+ .recipe>li{list-style:none;position:relative;padding-left:34px;margin:10px 0}
68
+ .recipe>li:before{counter-increment:s;content:counter(s);position:absolute;left:0;top:1px;width:24px;height:24px;border-radius:50%;background:var(--accent);color:var(--panel);font-size:13px;font-weight:700;display:flex;align-items:center;justify-content:center}
69
+ code{font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:12.5px;background:var(--bg);border:1px solid var(--line);border-radius:4px;padding:0 4px}
70
+ footer{margin-top:40px;color:var(--muted);font-size:12.5px}
71
+ @media (max-width:600px){
72
+ header h1{font-size:23px}
73
+ .bar{grid-template-columns:110px 1fr 46px}
74
+ }
75
+ </style>
76
+ </head>
77
+ <body>
78
+ <div class="wrap">
79
+
80
+ <header>
81
+ <h1>四模态病理对齐实验报告</h1>
82
+ <p class="sub">H&amp;E 图像 · 文本 · mIF 蛋白 · RNA,ImageBind 式对齐到 UNI2 H&amp;E 空间|结果截至 2026-10-22(含 13 种训练方式对比)</p>
83
+ </header>
84
+
85
+ <nav>
86
+ <a href="#verdict">总体结论</a><a href="#setup">数据与协议</a><a href="#real">训练过的配对</a>
87
+ <a href="#emergent">未一起训练的配对</a><a href="#virtual">虚拟数据校准</a><a href="#external">外部测试</a>
88
+ <a href="#encoders">编码器对比</a><a href="#text">文本清理</a><a href="#regimes">训练方式对比</a><a href="#recipe">最佳训练方案</a><a href="#next">下一步</a>
89
+ </nav>
90
+
91
+ <section id="verdict">
92
+ <div class="card verdict">
93
+ <strong>总体结论:</strong>H&amp;E↔mIF 很强,几乎能一一对上;H&amp;E↔文本和 H&amp;E↔RNA 中等;从未一起训练的模态之间(如 mIF↔RNA、文本↔RNA)能对上,约为瞎猜的 4–10 倍,但很弱。模型在同类组织上能迁移,在 DLPFC(脑)外部测试上失败。
94
+ </div>
95
+ <div class="kpis">
96
+ <div class="kpi"><div class="v">0.726</div><div class="l">H&amp;E↔mIF R@1(17 通道)<br>配对准确率 0.935</div></div>
97
+ <div class="kpi"><div class="v">0.237</div><div class="l">H&amp;E↔文本 R@1(TCGA)<br>R@10 0.73</div></div>
98
+ <div class="kpi"><div class="v">0.148</div><div class="l">H&amp;E↔RNA R@1(HEST)<br>R@10 0.55</div></div>
99
+ <div class="kpi"><div class="v">≈0.10</div><div class="l">mIF↔RNA,从未一起训练<br>约为瞎猜的 10 倍</div></div>
100
+ </div>
101
+ <p class="small muted">指标说明:R@1 = 从 100 个候选里第一个就找对的比例(瞎猜 0.01);配对准确率 = 100 对做一对一最优匹配后的正确率(瞎猜 0.01)。均为测试集、5 折平均、两个检索方向平均。</p>
102
+ </section>
103
+
104
+ <section id="setup">
105
+ <h2>数据与评估协议</h2>
106
+ <div class="tbl"><table>
107
+ <tr><th>模态</th><th>和 H&amp;E 配对的数据</th><th class="wrap">规模</th><th>划分(训练 / 验证 / 测试)</th></tr>
108
+ <tr><td>mIF(蛋白)</td><td>ORION 结直肠</td><td class="wrap">3,187 个 tile,17 个通道</td><td>按病人 5 折 + 官方划分</td></tr>
109
+ <tr><td>RNA</td><td>HEST-1k Visium</td><td class="wrap">9,484 个 spot,16 种器官,57 个研究</td><td>按研究/病人分组 5 折</td></tr>
110
+ <tr><td>文本</td><td>TCGA(PathGen 系列)</td><td class="wrap">6,144 张图,清理后 6,115 条真实文本</td><td>按病人 5 折</td></tr>
111
+ </table></div>
112
+ <ul>
113
+ <li><strong>只用真实配对训练。</strong>验证集只用于早停,结果全部来自测试集,病人或研究不会跨划分。</li>
114
+ <li><strong>虚拟数据只用于评估:</strong>MIPHEI 虚拟 mIF、STPath 虚拟 RNA、GPT few-shot 合成文本。</li>
115
+ <li><span class="tag warn">循环</span> 表示两侧都由同一张 H&amp;E 生成(如 H&amp;E↔由这张 H&amp;E 预测的虚拟 mIF),只能作参考,不能证明模型学到了什么。</li>
116
+ </ul>
117
+ </section>
118
+
119
+ <section id="real">
120
+ <h2>一、训练过的配对(真实数据)</h2>
121
+ <div class="tbl"><table>
122
+ <tr><th>配对</th><th>数据</th><th class="n">R@1</th><th class="n">R@10</th><th class="n">配对准确率</th><th class="wrap">评价</th></tr>
123
+ <tr><td>H&amp;E↔mIF(17 通道)</td><td>ORION 5 折</td><td class="n"><b>0.726</b> ±0.031</td><td class="n">0.989</td><td class="n"><b>0.935</b></td><td class="wrap">很强</td></tr>
124
+ <tr><td>H&amp;E↔mIF(16 通道)</td><td>ORION 5 折</td><td class="n">0.689</td><td class="n">0.984</td><td class="n">0.901</td><td class="wrap">通道越多越好</td></tr>
125
+ <tr><td>H&amp;E↔mIF(10 通道)</td><td>ORION 5 折</td><td class="n">0.644</td><td class="n">0.979</td><td class="n">0.863</td><td class="wrap"></td></tr>
126
+ <tr><td>H&amp;E↔mIF(17 通道)</td><td>ORION 官方测试</td><td class="n">0.665</td><td class="n">1.000</td><td class="n">0.948</td><td class="wrap">109 个 tile</td></tr>
127
+ <tr><td>H&amp;E↔文本</td><td>TCGA 5 折</td><td class="n"><b>0.237</b> ±0.012</td><td class="n">0.730</td><td class="n">0.248</td><td class="wrap">中等</td></tr>
128
+ <tr><td>H&amp;E↔RNA</td><td>HEST 5 折</td><td class="n"><b>0.148</b> ±0.026</td><td class="n">0.547</td><td class="n">0.166</td><td class="wrap">中等</td></tr>
129
+ </table></div>
130
+ <div class="bars">
131
+ <div class="bar"><span>H&amp;E↔mIF 17 通道</span><div class="track"><div class="fill" style="width:72.6%"></div><div class="chance" style="left:1%"></div></div><span class="val">0.726</span></div>
132
+ <div class="bar"><span>H&amp;E↔mIF 16 通道</span><div class="track"><div class="fill" style="width:68.9%"></div><div class="chance" style="left:1%"></div></div><span class="val">0.689</span></div>
133
+ <div class="bar"><span>H&amp;E↔mIF 10 通道</span><div class="track"><div class="fill" style="width:64.4%"></div><div class="chance" style="left:1%"></div></div><span class="val">0.644</span></div>
134
+ <div class="bar"><span>H&amp;E↔文本</span><div class="track"><div class="fill" style="width:23.7%"></div><div class="chance" style="left:1%"></div></div><span class="val">0.237</span></div>
135
+ <div class="bar"><span>H&amp;E↔RNA</span><div class="track"><div class="fill" style="width:14.8%"></div><div class="chance" style="left:1%"></div></div><span class="val">0.148</span></div>
136
+ <div class="legend">R@1,满刻度 1.0;红线 = 瞎猜(0.01)</div>
137
+ </div>
138
+ <ul>
139
+ <li><strong>H&amp;E↔RNA 在同一器官内很弱:</strong>只在同一器官内找时,脑 0.021、乳腺 0.040、肠 0.070。0.148 中相当一部分靠的是先认出器官。</li>
140
+ <li><strong>H&amp;E↔文本受限于文本本身:</strong>很多文本描述的是一类组织,而不是这张图独有的特征。按文本类型:caption 0.28、总结 0.29、开放问答 0.22、选择题 0.13。</li>
141
+ </ul>
142
+ </section>
143
+
144
+ <section id="emergent">
145
+ <h2>二、从未一起训练的配对(各自只和 H&amp;E 对齐)</h2>
146
+ <p>没有数据集同时测了这些模态的两边,所以一侧必须用虚拟数据。</p>
147
+ <div class="tbl"><table>
148
+ <tr><th>配对</th><th>数据</th><th class="n">R@1</th><th class="n">R@10</th><th class="n">配对准确率</th><th class="n">约为瞎猜</th></tr>
149
+ <tr><td>mIF(16 通道)↔RNA(STPath 虚拟)</td><td>ORION 5 折</td><td class="n">0.108</td><td class="n">0.512</td><td class="n">0.149</td><td class="n">11×</td></tr>
150
+ <tr><td>mIF(10 通道)↔RNA(STPath 虚拟)</td><td>ORION 5 折</td><td class="n">0.098</td><td class="n">0.495</td><td class="n">0.131</td><td class="n">10×</td></tr>
151
+ <tr><td>mIF↔文本(GPT 合成)</td><td>ORION 5 折</td><td class="n">0.074</td><td class="n">0.437</td><td class="n">0.072</td><td class="n">7×</td></tr>
152
+ <tr><td>文本↔RNA(虚拟)</td><td>TCGA 5 折</td><td class="n">0.056</td><td class="n">0.319</td><td class="n">0.057</td><td class="n">5.6×</td></tr>
153
+ <tr><td>文本↔mIF(MIPHEI 虚拟)</td><td>TCGA 5 折</td><td class="n">0.036</td><td class="n">0.237</td><td class="n">0.038</td><td class="n">3.6×</td></tr>
154
+ </table></div>
155
+ <ul>
156
+ <li>四个模态确实对齐到了同一个空间,但精度只有直接训练过的配对的 1/3 到 1/6。</li>
157
+ <li>链条上最弱的一环决定上限:H&amp;E↔文本和 H&amp;E↔RNA 本身只有 0.15–0.24。</li>
158
+ </ul>
159
+ </section>
160
+
161
+ <section id="virtual">
162
+ <h2>三、虚拟数据能否代替真实数据做验证</h2>
163
+ <p>校准方法:在同一批测试样本上,把真实数据换成虚拟数据,看配对效果保留多少。只算虚拟模型没训练过的样本。</p>
164
+ <div class="tbl"><table>
165
+ <tr><th>虚拟数据</th><th>校准对比</th><th class="n">真实</th><th class="n">虚拟</th><th>结论</th></tr>
166
+ <tr><td>MIPHEI 虚拟 mIF</td><td>H&amp;E↔mIF 配对准确率(ORION 官方测试,MIPHEI 未见过)</td><td class="n">0.921</td><td class="n">0.553</td><td><span class="tag ok">可用,约 0.6×</span></td></tr>
167
+ <tr><td>STPath 虚拟 RNA</td><td>H&amp;E↔RNA R@1(STPath 未见过的 spot)</td><td class="n">0.086</td><td class="n">0.080</td><td><span class="tag ok">可用</span></td></tr>
168
+ <tr><td>GPT 合成文本</td><td>H&amp;E↔文本 R@1(同一批 TCGA 图)</td><td class="n">0.219</td><td class="n">0.162</td><td><span class="tag ok">可用,约 0.75×,偏保守</span></td></tr>
169
+ <tr><td>GigaTIME 虚拟 mIF</td><td>H&amp;E↔mIF R@1(ORION 5 折)</td><td class="n">0.644</td><td class="n">0.038</td><td><span class="tag bad">不可用,已弃用</span></td></tr>
170
+ </table></div>
171
+ <ul class="small">
172
+ <li>MIPHEI 用 ORION 官方训练集训练过,因此只有官方测试切片(CRC02、CRC11)和 TCGA 对它是干净的。</li>
173
+ <li>通道均值和真实 mIF 的相关性:MIPHEI 0.70,GigaTIME 0.25。</li>
174
+ <li>直接用虚拟配对训练(文本↔虚拟 RNA / 虚拟蛋白)没有超过经 H&amp;E 间接对齐:蛋白 0.596 vs 0.678(AUROC),RNA 打平。所以虚拟数据只用于评估。</li>
175
+ </ul>
176
+ </section>
177
+
178
+ <section id="external">
179
+ <h2>四、外部测试:DLPFC(脑)</h2>
180
+ <p>spatialLIBD Visium,482 个 spot / 12 张切片 / 3 名供体。这 12 张切片原本也在 HEST 里,测试前已把整个 spatialLIBD 研究从训练中剔除。</p>
181
+ <div class="tbl"><table>
182
+ <tr><th>配对</th><th>类型</th><th class="n">R@1(100 候选,瞎猜 0.01)</th><th class="n">同切片内(35 候选,瞎猜 0.029)</th></tr>
183
+ <tr><td>H&amp;E↔RNA</td><td>真实,训练过的配对</td><td class="n">0.010</td><td class="n">0.031</td></tr>
184
+ <tr><td>RNA↔MIPHEI 虚拟 mIF</td><td>真实×虚拟</td><td class="n">0.008</td><td class="n">0.027</td></tr>
185
+ <tr><td>RNA↔合成文本</td><td>真实×虚拟</td><td class="n">0.010</td><td class="n">0.032</td></tr>
186
+ <tr><td>H&amp;E↔合成文本 <span class="tag warn">循环</span></td><td>参考</td><td class="n">0.022</td><td class="n">0.054</td></tr>
187
+ <tr><td>H&amp;E↔MIPHEI 虚拟 mIF <span class="tag warn">循环</span></td><td>参考</td><td class="n">0.017</td><td class="n">0.040</td></tr>
188
+ </table></div>
189
+ <ul>
190
+ <li><strong>全部在瞎猜水平。</strong>只在同一张切片内比较也一样,所以不是样本差异造成的。</li>
191
+ <li><strong>原因:</strong>脑皮层不同 spot 在 H&amp;E 上本来就很难区分(HEST ���部脑也只有 0.021),这批图视野只有 112 µm 且模糊。GPT 也把 59% 的 spot 写成了淋巴组织,只有 6% 认出是脑组织。</li>
192
+ </ul>
193
+ </section>
194
+
195
+ <section id="encoders">
196
+ <h2>五、每个模态最好的编码器</h2>
197
+ <p>按最终协议的划分逐折比较;文本那项在干净文本上重跑。“领先”= 最好减对比项;p 为 5 折配对 t 检验(5 折全胜时 p 最低约 0.06)。</p>
198
+ <div class="tbl"><table>
199
+ <tr><th>模态</th><th>最好</th><th class="wrap">对比(领先 / 赢几折 / p)</th><th class="wrap">结论</th></tr>
200
+ <tr><td>文本</td><td><b>BiomedCLIP</b> 0.237</td><td class="wrap">CONCH 文本 +0.021(5/5,p=0.03);PLIP +0.026(5/5,p=0.007);ImageBind +0.036(5/5,p=0.002)</td><td class="wrap"><span class="tag ok">明确最好</span></td></tr>
201
+ <tr><td>H&amp;E(对齐文本)</td><td>Phikon-v2 0.241 ≈ CONCH 0.241 ≈ UNI2 0.237</td><td class="wrap">GigaPath 0.223(UNI2 +0.014,4/5,p=0.05)</td><td class="wrap">三者打平</td></tr>
202
+ <tr><td>H&amp;E(对齐 mIF)</td><td><b>UNI2</b> 0.727</td><td class="wrap">GigaPath +0.009(不显著);CONCH +0.155(5/5,p&lt;0.001)</td><td class="wrap">UNI2 ≈ GigaPath ≫ CONCH</td></tr>
203
+ <tr><td>H&amp;E(对齐 RNA)</td><td><b>UNI2</b> 0.148</td><td class="wrap">GigaPath +0.035(4/5,p=0.05)</td><td class="wrap">UNI2</td></tr>
204
+ <tr><td>mIF</td><td><b>ConvNeXt-T</b>(从头训练)0.758</td><td class="wrap">VirTues(冻结)+0.030(5/5,p=0.07)</td><td class="wrap">差距小;VirTues 跨模态更好</td></tr>
205
+ <tr><td>RNA</td><td>Geneformer-V2 0.159</td><td class="wrap">scGPT +0.005(3/5,不显著);MLP +0.011(4/5,p=0.05)</td><td class="wrap">打平</td></tr>
206
+ </table></div>
207
+ <h3>H&amp;E × 文本编码器(干净文本,R@1)</h3>
208
+ <div class="tbl"><table>
209
+ <tr><th>H&amp;E \ 文本</th><th class="n">BiomedCLIP</th><th class="n">CONCH 文本</th><th class="n">PLIP</th><th class="n">ImageBind</th></tr>
210
+ <tr><td>Phikon-v2</td><td class="n"><b>0.241</b></td><td class="n">0.223</td><td class="n">0.211</td><td class="n">0.207</td></tr>
211
+ <tr><td>CONCH</td><td class="n"><b>0.241</b></td><td class="n">0.221</td><td class="n">0.213</td><td class="n">0.209</td></tr>
212
+ <tr><td>UNI2</td><td class="n"><b>0.237</b></td><td class="n">0.216</td><td class="n">0.211</td><td class="n">0.201</td></tr>
213
+ <tr><td>GigaPath</td><td class="n">0.223</td><td class="n">0.201</td><td class="n">0.191</td><td class="n">0.189</td></tr>
214
+ </table></div>
215
+ <p class="small muted">UNI2 是唯一在任何配对上都没被显著超过的 H&amp;E 编码器;Phikon-v2 只测了文本(HEST 只提供 UNI2 和 GigaPath 的特征)。CONCH 在文本上好,但 H&amp;E↔mIF 的配对准确率只有 UNI2 的一半。</p>
216
+ </section>
217
+
218
+ <section id="text">
219
+ <h2>六、文本清理</h2>
220
+ <ul>
221
+ <li><strong>去掉 365 / 6,480 条垃圾文本:</strong>353 条只有选择题答案字母(如 “A A B B”),4 条 “error error”,8 条少于 5 个词的残缺答案。</li>
222
+ <li><strong>256 张图因此没有任何真实文本:</strong>它们保留在原划分里,用 3-shot GPT 生成描述,只用于评估。H&amp;E↔合成文本 0.150,和有真实文本的校准集(0.162)一致。</li>
223
+ <li><strong>用干净文本重训后:</strong>H&amp;E↔文本 0.229 → 0.237。但旧模型在干净测试集上也有 0.236,所以提升几乎全部来自测试集变干净;重训本身 +0.001(5 折 3 胜 2 负),属于噪声。</li>
224
+ </ul>
225
+ </section>
226
+
227
+ <section id="regimes">
228
+ <h2>七、训练方式对比:分开训练 vs 联合训练</h2>
229
+ <p>13 种方式,统一用同一套划分、同一份干净真实数据、同一种对齐头和优化器;虚拟数据只用于评估。数值为 R@1(5 折平均)。“相对 S1”= 各配对 R@1 除以 S1 后取平均。</p>
230
+ <div class="tbl"><table>
231
+ <tr><th>方式</th><th class="n">H&amp;E↔mIF</th><th class="n">H&amp;E↔RNA</th><th class="n">H&amp;E↔文本</th><th class="n">mIF↔RNA(虚)</th><th class="n">mIF↔文本(合)</th><th class="n">文本↔RNA(虚)</th><th class="n">文本↔mIF(虚)</th><th class="n">训练过的<br>相对 S1</th><th class="n">未一起训练<br>相对 S1</th></tr>
232
+ <tr><td>S1 分开·冻结锚点(原方案)</td><td class="n">0.680</td><td class="n">0.148</td><td class="n">0.234</td><td class="n">0.108</td><td class="n">0.076</td><td class="n">0.060</td><td class="n">0.038</td><td class="n">1.00</td><td class="n">1.00</td></tr>
233
+ <tr><td>S2 分开·双塔(CLIP 式)</td><td class="n"><b>0.794</b></td><td class="n">0.130</td><td class="n">0.195</td><td class="n">0.019</td><td class="n">0.022</td><td class="n">0.014</td><td class="n">0.013</td><td class="n">0.96</td><td class="n"><span class="tag bad">0.26</span></td></tr>
234
+ <tr><td>S3 分开·冻结·全线性头</td><td class="n">0.642</td><td class="n">0.156</td><td class="n">0.237</td><td class="n"><b>0.123</b></td><td class="n">0.070</td><td class="n">0.069</td><td class="n">0.038</td><td class="n">1.00</td><td class="n">1.05</td></tr>
235
+ <tr><td>S4 分开·冻结·mIF 用 MLP,RNA/文本用线性</td><td class="n">0.680</td><td class="n">0.152</td><td class="n">0.234</td><td class="n">0.117</td><td class="n">0.074</td><td class="n"><b>0.071</b></td><td class="n">0.037</td><td class="n">1.01</td><td class="n">1.05</td></tr>
236
+ <tr><td>J1 联合·冻结锚点</td><td class="n">0.706</td><td class="n">0.148</td><td class="n"><b>0.237</b></td><td class="n">0.094</td><td class="n">0.065</td><td class="n">0.056</td><td class="n">0.031</td><td class="n">1.02</td><td class="n">0.87</td></tr>
237
+ <tr><td>J2 联合·共享可训练 H&amp;E 头</td><td class="n">0.761</td><td class="n">0.147</td><td class="n">0.204</td><td class="n">0.061</td><td class="n">0.060</td><td class="n">0.044</td><td class="n">0.031</td><td class="n">0.99</td><td class="n">0.72</td></tr>
238
+ <tr><td>J3 J2 + 按数据量采样</td><td class="n">0.740</td><td class="n">0.138</td><td class="n">0.187</td><td class="n">0.063</td><td class="n">0.060</td><td class="n">0.039</td><td class="n">0.031</td><td class="n">0.94</td><td class="n">0.70</td></tr>
239
+ <tr><td>J4 J2 + 锚点蒸馏 λ=1</td><td class="n">0.765</td><td class="n">0.144</td><td class="n">0.202</td><td class="n">0.062</td><td class="n">0.058</td><td class="n">0.043</td><td class="n">0.030</td><td class="n">0.99</td><td class="n">0.71</td></tr>
240
+ <tr><td>J4b J2 + 锚点蒸馏 λ=10</td><td class="n">0.768</td><td class="n">0.149</td><td class="n">0.209</td><td class="n">0.067</td><td class="n">0.058</td><td class="n">0.047</td><td class="n">0.030</td><td class="n">1.01</td><td class="n">0.74</td></tr>
241
+ <tr><td>J5 联合·UNI2 + 共享残差适配器</td><td class="n">0.762</td><td class="n">0.142</td><td class="n">0.201</td><td class="n">0.058</td><td class="n">0.059</td><td class="n">0.044</td><td class="n">0.029</td><td class="n">0.98</td><td class="n">0.71</td></tr>
242
+ <tr><td>J6 J2 + 不确定性自动加权</td><td class="n">0.765</td><td class="n">0.136</td><td class="n">0.195</td><td class="n">0.057</td><td class="n">0.055</td><td class="n">0.041</td><td class="n">0.027</td><td class="n">0.96</td><td class="n">0.66</td></tr>
243
+ <tr><td>J7 两阶段:S1 → 联合残差微调</td><td class="n">0.776</td><td class="n">0.150</td><td class="n">0.234</td><td class="n">0.100</td><td class="n">0.076</td><td class="n">0.055</td><td class="n">0.035</td><td class="n">1.05</td><td class="n">0.94</td></tr>
244
+ <tr style="background:var(--accent-soft)"><td><b>J8 两阶段:S4 → 联合残差微调</b></td><td class="n">0.762</td><td class="n"><b>0.164</b></td><td class="n">0.232</td><td class="n">0.112</td><td class="n">0.073</td><td class="n">0.068</td><td class="n">0.035</td><td class="n"><b>1.07</b></td><td class="n"><b>1.01</b></td></tr>
245
+ </table></div>
246
+ <div class="bars">
247
+ <div class="bar"><span>S1 原方案</span><div class="track"><div class="fill" style="width:50%"></div></div><span class="val">1.00</span></div>
248
+ <div class="bar"><span>S2 双塔</span><div class="track"><div class="fill" style="width:48%"></div></div><span class="val">0.96</span></div>
249
+ <div class="bar"><span>J2 共享 H&amp;E 头</span><div class="track"><div class="fill" style="width:49.7%"></div></div><span class="val">0.99</span></div>
250
+ <div class="bar"><span>J7 两阶段</span><div class="track"><div class="fill" style="width:52.5%"></div></div><span class="val">1.05</span></div>
251
+ <div class="bar"><span><b>J8 两阶段 + 混合头</b></span><div class="track"><div class="fill" style="width:53.6%"></div></div><span class="val">1.07</span></div>
252
+ <div class="legend">训练过的配对,相对 S1(满刻度 2.0)</div>
253
+ <div class="bar"><span>S1 原方案</span><div class="track"><div class="fill b2" style="width:50%"></div></div><span class="val">1.00</span></div>
254
+ <div class="bar"><span>S2 双塔</span><div class="track"><div class="fill b2" style="width:13.2%"></div></div><span class="val">0.26</span></div>
255
+ <div class="bar"><span>J2 共享 H&amp;E 头</span><div class="track"><div class="fill b2" style="width:36.1%"></div></div><span class="val">0.72</span></div>
256
+ <div class="bar"><span>J7 两阶段</span><div class="track"><div class="fill b2" style="width:47%"></div></div><span class="val">0.94</span></div>
257
+ <div class="bar"><span><b>J8 两阶段 + 混合头</b></span><div class="track"><div class="fill b2" style="width:50.5%"></div></div><span class="val">1.01</span></div>
258
+ <div class="legend">从未一起训练的配对,相对 S1(满刻度 2.0)</div>
259
+ </div>
260
+ <ul>
261
+ <li><strong>从头训练 H&amp;E 侧(S2、J2–J6):</strong>H&amp;E↔mIF 涨 0.08–0.11,但 H&amp;E↔文本降 0.03–0.05,从未一起训练的配对损失 26–74%。共享的 H&amp;E 头被最容易的 mIF 任务“拉走”。按数据量采样和不确定性加权更差;蒸馏到 UNI2 结构只略有帮助。</li>
262
+ <li><strong>联合但锚点冻结(J1):</strong>只是训练步数变了,mIF +0.026,但未一起训练的配对 −13%。</li>
263
+ <li><strong>线性头:</strong>RNA 和文本用线性头,跨模态迁移比 MLP 更好(+5%);mIF 仍需要 MLP。</li>
264
+ <li><strong>J8 对比 S1(5 折配对):</strong>H&amp;E↔mIF +0.083(5/5,p=0.01),H&amp;E↔RNA +0.015(5/5,p=0.03),文本↔RNA(虚) +0.008(5/5,p=0.02);其余配对差 ≤0.004,不显著。配对准确率 mIF 0.897→0.929,RNA 0.172→0.198。</li>
265
+ </ul>
266
+ </section>
267
+
268
+ <section id="recipe">
269
+ <h2>八、最佳训练方案</h2>
270
+ <ol class="recipe">
271
+ <li><strong>两阶段训练(J8,13 种方式中最好):</strong>
272
+ <ul>
273
+ <li>第一阶段:冻结 UNI2 当锚点,每个模态各自分开训练对齐头(ImageBind 做法)。</li>
274
+ <li>第二阶段:所有头一起联合微调,同时给 UNI2 加一个三个数据集共享、初始化为零的残差适配器;lr 1e-4,1000 步,三个损失相加,加相似度蒸馏(λ=1),按三项验证 R@1 的几何平均早停。</li>
275
+ <li>不要从头训练 H&amp;E 侧(双塔或共享 H&amp;E 头):H&amp;E↔mIF 会更高,但文本和跨模态对齐明显变差。</li>
276
+ </ul>
277
+ </li>
278
+ <li><strong>编码器:</strong>
279
+ <ul>
280
+ <li>H&amp;E:<b>UNI2</b></li>
281
+ <li>文本:<b>BiomedCLIP</b>(冻结)+ <b>线性</b>对齐头</li>
282
+ <li>mIF:<b>VirTues</b>(冻结)+ <b>MLP</b> 对齐头,尽量用全部通道;只关心 H&amp;E↔mIF 时 ConvNeXt-T 从头训练高 0.03</li>
283
+ <li>RNA:2000 个高变基因,log1p CP10k,<b>线性</b>对齐头(Geneformer / scGPT 打平);外部数据按数据集各自 z-score</li>
284
+ </ul>
285
+ </li>
286
+ <li><strong>对齐头与超参数:</strong>MLP 为 3 层(隐藏 512,LayerNorm),对称 InfoNCE(同一张图有多条文本时都当正例),可学习温度(初始 0.07),AdamW lr 3e-4、weight decay 0.05、OneCycle,batch 256,60–100 epoch,每张 H&amp;E 8 个增强视图训练时随机取一个,按验证集 R@1 早停。</li>
287
+ <li><strong>数据:</strong>只用真实配对;按病人或研究划分(按 tile 随机划分会偏乐观);训练前清掉垃圾文本。</li>
288
+ <li><strong>不要用虚拟配对训练。</strong>直接训练没有超过经 H&amp;E 间接对齐,蛋白还更差;虚拟数据只用于评估。</li>
289
+ </ol>
290
+ </section>
291
+
292
+ <section id="next">
293
+ <h2>九、下一步最值得做的</h2>
294
+ <ul>
295
+ <li><strong>找同一组织同时测了两个模态的真实数据</strong>(如 Visium + CODEX 同切片),这样 RNA↔mIF 能直接训练和直接测,不再依赖虚拟数据。</li>
296
+ <li><strong>提高 RNA 在同一器官内的区分能力:</strong>同器官困难负样本,或更大的 spot 视野。</li>
297
+ <li><strong>文本:</strong>以 caption 和总结类长文本为主训练,弱化选择题。</li>
298
+ </ul>
299
+ </section>
300
+
301
+ <footer>
302
+ <p>许可说明:MIPHEI-ViT 权重仅限非商业学术使用;GigaTIME 权重仅限研究使用(已弃用)。合成文本由 Azure OpenAI 生成,仅用于评估。</p>
303
+ <p>代码:<code>imagebind_exp/</code> 中的 <code>33_final_eval.py</code>(最终协议)、<code>38_</code>/<code>39_</code>(外部测试与检查)、<code>40_clean_text.py</code>、<code>41_text_enc_clean.py</code>、<code>42_train_regimes.py</code>(训练方式对比);完整数字见 <code>RESULTS.md</code> 和 <code>results/*.csv</code>。</p>
304
+ </footer>
305
+
306
+ </div>
307
+ </body>
308
+ </html>