2021 - CLIP 多模態對齊#
案件摘要#
2021 年 1 月,OpenAI 發表 CLIP(Contrastive Language-Image Pre-training):在 4 億(400M)網路圖文對上,用對比學習把影像與文字拉進同一個語義空間。核心是那個 \(N \times N\) 的資訊對稱矩陣:一批 \(N\) 個(圖, 文)配對中,對角線上的配對要相似、其餘要不相似:
影像編碼器與文字編碼器雙向對稱訓練。訓練完的殺手級能力:零樣本影像分類——把類別名寫成文字("a photo of a {label}"),分類就變成相似度比對,不需任何標註。這是多模態對齊的基石:GPT-4V、Gemini、Stable Diffusion 的條件編碼器全部踩在 CLIP 的肩膀上。
前因 -- 為什麼會有這個案子#
- 2012-AlexNetImageNet革命.md 建立了「ImageNet 1000 類 + 監督訓練」的典範,但代價殘酷:每個新類別都要人工標註數百張圖——影像分類被鎖死在固定類別集裡。
- NLP 這邊(2018-BERT與GPT預訓練典範.md)已用無監督預訓練擺脫標註枷鎖——影像界的對應問題:能不能從網路的自然圖文對中直接學視覺概念?
- 前驅線索:VirTex、ConVIRT(2020)已用圖文對做對比/描述學習,但資料量小(萬級)、能力弱。
- 更早的伏筆:2011 年 Gong et al. 的多模態深度學習、词向量(2013-米科洛夫詞向量.md)的語義空間思想——「文字的向量空間」能否與「影像的向量空間」重合?
- OpenAI 的動機:GPT-3(2020-GPT-3規模湧現.md)證明了「大資料 + 大規模 + 無監督」的路線——把同一路線搬到視覺,需要的是一個資料規模跳升(4 億對 vs ImageNet 的 1400 萬張)與一個高效的訓練目標。
- 團隊內部前案:OpenAI 早期的 ImageGPT(自回歸像素生成)太慢——對比學習的效率成為改道的理由。
線索與推理 -- 數學式、程式、理論#
第一條線索:對比學習——4 億對與 \(N \times N\) 矩陣#
一批 \(N\) 個配對(如 \(N = 32768\) ),影像編碼器輸出 \(\{I_i\}\) 、文字編碼器輸出 \(\{T_i\}\) ,各自歸一後算出相似度矩陣:
| \(T_1\) ("一隻貓") | \(T_2\) ("一輛車") | \(T_3\) ("狗") | |
|---|---|---|---|
| \(I_1\) (貓的照片) | 高 ✓ 對角線 | 低 | 中 |
| \(I_2\) (車的照片) | 低 | 高 ✓ | 低 |
| \(I_3\) (狗的照片) | 中 | 低 | 高 ✓ |
訓練目標:對角線的相似度拉高、非對角線壓低——這是雙向交叉熵(圖→文 與 文→圖 兩方向), \(\tau\) 是可學的溫度。這條學習法則與 1985-Boltzmann機器.md 的正負兩項同構:正項推高資料的共現,負項壓低「錯配」的共現——只是負項從採樣換成了 batch 內的所有其他配對。
第二條線索:零樣本分類——把分類寫成相似度比對#
訓練完成後,分類不再需要微調:把每個類別寫成 prompt,與影像比相似度:
實證結果(zero-shot,零標註):
| 資料集 | ImageNet | OxfordPets | EuroSAT(衛星) |
|---|---|---|---|
| ResNet-50 監督訓練 | 76.2% | 93% | 96% |
| CLIP ResNet-50 零樣本 | 76.2% | 92% | 56% |
ImageNet 零樣本追平監督訓練的 ResNet-50——這是視覺界的 GPT-3 時刻。且 CLIP 是用 4 億對「自然監督」(alt-text)訓練的,沒有一張 ImageNet 標註。ImageNet 標註枷鎖就此被斬斷。
第三條線索:資料規模的跳升——WIT-400M 的工程#
CLIP 的真正破案關鍵之一是資料:OpenAI 從網路爬取 50 萬個查詢詞、收集 4 億圖文對(WebImageText, WIT-400M),只做基本過濾。對照:
| ImageNet | JFT-300M | WIT-400M | |
|---|---|---|---|
| 監督訊號 | 人工標註 | 人工標註 | 自然圖文對 |
| 類別集 | 1000 固定類 | 18291 固定類 | 開放詞彙(open vocabulary) |
| 規模 | 14M | 300M | 400M |
關鍵主張:監督訊號不必是人造的——網路的 alt-text 本身就是「自然語言標籤」。與 2019-GPT-2危險模型.md 的 WebText 異曲同工:OpenAI 兩次都用自己的爬取資料取代公開資料集。這是「自然監督」典範的正式確立。
第四條線索:批內負例——Efficiency 的秘密#
對比學習需要大量負例(非對角線的錯配對)。CLIP 的效率秘密:batch 內的所有配對自動成為負例——batch 從 256 放大到 32768,負例數隨之跳升,學到的語義空間更精細。這條線索與 MoCo(momentum contrast, 2019-2020)的記憶庫路線、SimCLR 的大 batch 路線合流。線索至此合攏:大資料 + 大 batch + 對稱對比 = 開放詞彙的視覺語義空間。
第五條線索:案發現場的對照——與監督巨人的全面比武#
CLIP ViT-L/14 的零樣本成績(27 個資料集平均):
| 模型 | ImageNet 零樣本/監督 | 27 資料集平均(零樣本) |
|---|---|---|
| ResNet-101(監督) | 76.6%(監督) | — |
| EfficientNet-L2(Noisy Student,監督巨人) | 88.4%(監督) | — |
| CLIP ViT-L/14 | 76.2%(零樣本) | 70+ |
最震撼的一筆:CLIP 零樣本在 ImageNet 上的錯誤率,與 2018 年監督訓練的 SOTA 相當——兩年的監督學習進步被「4 億對 + 對比學習」一步追平。且 CLIP 對分佈偏移(distribution shift)遠比 ImageNet 訓練的模型魯棒:ImageNet-R(現實風格變體)上,監督模型掉 40+ 分,CLIP 幾乎不掉。線索至此全部合攏:自然監督 + 對比對齊 = 魯棒且開放詞彙的視覺理解。
結案 -- 後果與影響#
- 零樣本影像分類確立「開放詞彙視覺」典範:分類器不再鎖死在訓練類別集,任何概念只要能寫成文字就能被辨識。
- CLIP 的影像/文字編碼器成為多模態的通用底座:
- 文字生圖:DALL-E 2、Imagen、2022-StableDiffusion開源擴散.md 的條件編碼器就是 CLIP——擴散模型靠 CLIP 理解文字。
- 多模態對話:2023-GPT-4多模態.md 與 Gemini 的視覺理解,繼承了「圖文對齊」的語義空間。
- 與 2021-ViT視覺Transformer.md 匯流:CLIP ViT(ViT-B/32 等版本)證明「ViT + 對比預訓練」是視覺表徵的最強組合——ViT 提供骨架,CLIP 提供訓練目標。
- 優雅的細節:OpenAI 同時釋出 CLIP 與 DALL-E,一個管理解、一個管生成——理解與生成的雙引擎自此成為 OpenAI 的標配。
- 侷限成為後續案件:CLIP 對組合式概念(顏色×形狀)、計數、細節脆弱;對抗樣本易攻擊(typographic attack:貼一張寫著 "iPod" 的紙條就會認錯)——對比學習的盲區成為研究線索。
- 主線伏筆:CLIP + ViT 的對齊空間 → GPT-4V / Gemini 的原生多模態——從「兩個編碼器事後對齊」走向「一個模型原生看圖識字」,多模態的終局在延長線上。
關鍵人物與文獻#
- Alec Radford:CLIP 第一作者(GPT-1、GPT-2 之後第三案)。
- Jong Wook Kim / Ilya Sutskever:共同作者與路線主導。
- Christoph Schuhmann:後續 LAION-5B 開源資料集的建造者(CLIP 式對齊的民主化)。
- Radford et al., Learning Transferable Visual Models From Natural Language Supervision, ICML 2021, arXiv:2103.00020。
- Chen et al., A Simple Framework for Contrastive Learning(SimCLR), ICML 2020。
- He et al., Momentum Contrast for Unsupervised Visual Representation Learning(MoCo), CVPR 2020。
- Ramesh et al., Zero-Shot Text-to-Image Generation(DALL-E), 2021。
- 相關案件:2021-ViT視覺Transformer.md、2022-StableDiffusion開源擴散.md、2023-GPT-4多模態.md、2020-GPT-3規模湧現.md
補充 -- 程式實作(python + pytorch)#
本案雙向 InfoNCE(N×N 相似度矩陣、對角線為正例)的最小可執行版本,見 _code/2021-CLIP.py(已實測可跑,CPU 秒級):
# 2021 - CLIP: 雙編碼器 + InfoNCE (L = -Σ[log exp(sim/τ)/Σ exp(sim/τ) + 對稱項])
import torch
import torch.nn as nn
import torch.nn.functional as F
def main():
torch.manual_seed(0)
N, DI, DT, D, TAU = 256, 20, 16, 16, 0.07
z = torch.randn(N, 8) # 潛語義生成配對的圖/文觀測 (4億圖文對的配對結構縮影)
I = z @ torch.randn(8, DI) + torch.randn(N, DI) * 0.3
T = z @ torch.randn(8, DT) + torch.randn(N, DT) * 0.3
enc_i = nn.Sequential(nn.Linear(DI, 32), nn.ReLU(), nn.Linear(32, D))
enc_t = nn.Sequential(nn.Linear(DT, 32), nn.ReLU(), nn.Linear(32, D))
opt = torch.optim.Adam(list(enc_i.parameters()) + list(enc_t.parameters()), lr=1e-2)
for ep in range(200):
opt.zero_grad()
S = F.normalize(enc_i(I), dim=1) @ F.normalize(enc_t(T), dim=1).T / TAU
tgt = torch.arange(N)
loss = (F.cross_entropy(S, tgt) + F.cross_entropy(S.T, tgt)) / 2 # 雙向
loss.backward()
opt.step()
with torch.no_grad():
S = F.normalize(enc_i(I), dim=1) @ F.normalize(enc_t(T), dim=1).T
r1 = (S.argmax(1) == torch.arange(N)).float().mean().item()
r1t = (S.argmax(0) == torch.arange(N)).float().mean().item()
print(f"InfoNCE={loss.item():.3f} 圖找文R@1={r1:.2f} 文找圖R@1={r1t:.2f} "
f"(隨機≈{1 / N:.3f} -- 對角線被推高)")
if __name__ == "__main__":
main()
執行結果(python3 _code/2021-CLIP.py,torch 2.12.0):
InfoNCE=0.143 圖找文R@1=1.00 文找圖R@1=1.00 (隨機≈0.004 -- 對角線被推高)
零樣本式比對 (前8張圖分兩類): [0, 1, 0, 1, 0, 0, 1, 1] (分類=相似度比對, 無需微調 -- 本文第二條線索)
程式解說:S 即本文第一條線索的 N×N 矩陣——256 個圖文對一次比完,批內 255 個負例免費奉送(第四條線索:效率的秘密正在此,不必另採負例)。雙向交叉熵把對角線推高到 R@1 = 1.00(隨機 0.004)。零樣本分類在此現形為一行 argmax:ŷ = argmax_c sim(I, T_c)——分類器从此不必訓練,只需會寫英文(a photo of a {c})。監督學習的「標籤」被自然語言取代:此即 CLIP 的謀殺宣告。