清华+智谱的这篇论文和DeepSeek-OCR是同一赛道的两种打法,让我用最简单的方式讲清楚。
🎯 核心思想(一句话版)
把书变成照片给AI看,比一个字一个字读给它听更高效。
💡 背景动机:为什么要压缩?
传统LLM的困境
《简爱》小说 = 24万个token
传统LLM:
├─ 需要24万token的上下文窗口
├─ 内存消耗:O(n²) 爆炸式增长
├─ 训练成本:天文数字
└─ 推理速度:极慢
结果:根本跑不动!
Glyph的解决方案
《简爱》小说 → 渲染成图片 → 8万个视觉token
压缩比:24万 ÷ 8万 = 3×
为什么可行?
因为一张图片可以包含几百个字符,
而VLM只需要几百个视觉token就能编码这张图!
🔧 实现方法:三步走
第1步:持续预训练(教VLM读"照片书")
# 伪代码展示核心逻辑
def continual_pretraining():
# 准备训练数据
long_texts = load_books_and_documents()
# 渲染成多种风格
rendering_styles = [
"document_style", # 像Word文档
"web_style", # 像网页
"code_style", # 像代码编辑器
"dark_mode" # 深色主题
]
for text in long_texts:
for style in rendering_styles:
# 渲染文本为图像
images = render_text_to_images(text, style)
# 训练任务
tasks = [
ocr_task(images), # 让模型读图上的字
interleaved_lm(images), # 图文混合理解
generation_task(images) # 看图生成文字
]
train_model(tasks)
# 输出:Glyph-Base(会读"照片书"的基础模型)
类比:这就像教小孩认字,既要教他读印刷体,也要教他读手写体,还要教草书、楷书……
第2步:LLM驱动的遗传搜索(找最佳"拍照"参数)
这是论文最有趣的部分!
问题:如何渲染最优?
渲染参数(部分):
├─ DPI(分辨率):72 vs 120 vs 300?
├─ 字体大小:9pt vs 12pt?
├─ 页面尺寸:A4 vs Letter?
├─ 行高:紧凑 vs 宽松?
├─ 颜色:黑底白字 vs 白底黑字?
└─ ... 共20+个参数
组合空间:几乎无限大!
解决方案:让GPT-4帮忙搜索
def llm_driven_genetic_search():
# 初始化:随机生成配置
population = random_sample_configs(n=10)
for generation in range(5): # 论文中跑了5轮
# 1. 评估每个配置
results = []
for config in population:
images = render_with_config(validation_set, config)
accuracy = evaluate(model, images)
compression = calculate_compression(images)
results.append({
"config": config,
"accuracy": accuracy,
"compression": compression,
"score": balance(accuracy, compression)
})
# 2. 让GPT-4分析结果,建议改进
prompt = f"""
这是当前配置的评估结果:
{results}
请分析哪些参数影响了性能,
建议如何变异/交叉配置以获得更好的trade-off。
"""
suggestions = call_gpt4(prompt)
# 3. 根据GPT-4建议生成新配置
population = mutate_and_crossover(population, suggestions)
return best_config_from_history
# 输出:最优渲染配置
类比:这就像拍证件照,摄影师会调整光线、角度、背景……让GPT-4当"摄影指导",告诉你怎么调最好看。
论文的实际最优配置(Table 8和Figure 6):
最优配置:
dpi: 72 # 较低分辨率(平衡清晰度和压缩)
font_size: 9pt # 较小字体(塞更多字)
font_family: Verdana # 易读字体
page_size: 595×842 # A4尺寸
line_height: 10pt # 字体大小+1
alignment: LEFT # 左对齐
bg_color: #FFFFFF # 白底
font_color: #000000 # 黑字
margins: 10pt # 边距
压缩比: 3-4×
准确率: 与Qwen3-8B相当
第3步:后训练(精雕细琢)
def post_training(glyph_base, optimal_config):
# 用最优配置渲染所有训练数据
training_data = render_all_with_config(sft_data, optimal_config)
# 阶段1:监督微调
for epoch in sft_epochs:
for instruction, rendered_images, response in training_data:
# 加入思维链格式
response_with_thinking = f"""
<think>
我看到图片上有{count_words(rendered_images)}个字...
关键信息在第3页...
</think>
{response}
"""
train(instruction, rendered_images, response_with_thinking)
# 阶段2:强化学习(GRPO)
for iteration in rl_iterations:
# 采样多个回答
responses = sample_multiple(model, instruction, rendered_images, n=16)
# 用LLM judge打分
rewards = [
llm_judge_score(r, ground_truth) + # 准确性奖励
format_reward(r) + # 格式奖励
ocr_alignment_reward(r, images) # OCR对齐奖励
for r in responses
]
# 用GRPO更新策略
update_policy(responses, rewards)
return glyph # 最终模型
# 输出:Glyph(生产级模型)
类比:
- SFT = 老师手把手教,一步步示范
- RL = 自己做习题,根据对错调整策略
📊 效果对比:直观数据
性能对比
| 模型 | 上下文长度 | Token数 | LongBench | MRCR |
|---|---|---|---|---|
| Qwen3-8B | 128K | 128K | 47.46 | 23.02 |
| Glyph | 384K | 128K | 50.56 | 25.81 |
解读:
- Glyph用128K token处理了384K token的文本(3×压缩)
- 性能不降反升!
速度对比(Figure 4数据)
128K token输入:
预填充(Prefill):
├─ 传统LLM: 1.0x(基准)
└─ Glyph: 4.8x 快 ⚡
解码(Decoding):
├─ 传统LLM: 1.0x
└─ Glyph: 4.4x 快 ⚡
训练(SFT):
├─ 传统LLM: 1.0x
└─ Glyph: 2.0x 快 ⚡
🆚 Glyph vs DeepSeek-OCR:核心差异
| 维度 | DeepSeek-OCR | Glyph |
|---|---|---|
| 目标 | 批量生成训练数据 | 实时长文本理解 |
| 压缩比 | 10-20× | 3-4× |
| 准确率容忍度 | 可接受3-5%错误 | 需要接近100% |
| 应用场景 | 内部数据引擎 | 面向用户产品 |
| 延迟敏感度 | 不敏感(离线) | 敏感(在线) |
| 搜索方法 | 无(手动设计) | LLM驱动遗传搜索 |
形象比喻
DeepSeek-OCR = 工厂扫描仪
├─ 目标:快速批量扫描
├─ 可接受:偶尔识别错误(后续数据清洗)
└─ 优势:吞吐量巨大(日产33M页)
Glyph = 精密阅读器
├─ 目标:实时理解长文档
├─ 要求:高准确率(用户直接交互)
└─ 优势:速度快、效果好
🔬 关键技术洞察
1. 为什么视觉压缩可行?
信息密度对比
# 文本表示
text = "Hello World"
text_tokens = tokenizer(text)
# 输出: [15339, 4435] # 2个token
# 视觉表示
image = render_to_image(text, dpi=72, font_size=9)
vision_tokens = vision_encoder(image)
# 输出: [v1, v2, ..., v64] # 64个视觉token,但包含整行文字!
# 压缩效果
if len("Hello World " * 100) == 1200_chars:
text_tokens_needed = 200
vision_tokens_needed = 64 # 一张图搞定
compression_ratio = 200 / 64 = 3.1×
关键:一个视觉token可以编码多个文字token的信息!
2. LLM驱动搜索的妙处
传统遗传算法 vs LLM驱动搜索
传统GA:
├─ 随机变异 → 盲目试探
├─ 需要大量迭代(几千次)
└─ 效率低
LLM驱动搜索:
├─ GPT-4分析 → 有理有据的建议
├─ 只需5轮×200步 = 1000次评估
└─ 论文实测:找到接近最优解
GPT-4的典型建议(推测):
"当前DPI=120时,准确率95%但压缩比只有2×。
建议:降低DPI到72-96,可能牺牲2-3%准确率,
但压缩比能提升到3-4×,整体性价比更高。"
3. 多阶段训练的必要性
为什么不能一步到位?
如果直接用最优配置训练:
❌ 模型只见过一种渲染风格
❌ 泛化能力差(换个字体就懵)
❌ 无法应对多样化文档
Glyph的策略:
✅ 预训练:多样化风格 → 鲁棒性
✅ 搜索:找最优配置 → 效率
✅ 后训练:专门优化 → 性能
类比:
预训练 = 通识教育(什么书都读)
搜索 = 找专业方向(物理还是化学?)
后训练 = 专业深造(成为专家)
🎨 可视化示例
渲染效果对比
原始文本(1000 tokens):
┌────────────────────────────────────┐
│ In a hole in the ground there │
│ lived a hobbit. Not a nasty, dirty,│
│ wet hole, filled with the ends of │
│ worms and an oozy smell, nor yet a │
│ dry, bare, sandy hole with nothing │
│ in it to sit down on or to eat: it │
│ was a hobbit-hole, and that means │
│ comfort... │
│ [... 继续992个tokens ...] │
└────────────────────────────────────┘
渲染后(DPI=72, font-size=9pt):
┌──────────────────────┐
│ [密集的文字图片] │ ← 这一张图 = 256 vision tokens
│ 包含约800 text tokens │
└──────────────────────┘
┌──────────────────────┐
│ [密集的文字图片] │ ← 再一张 = 256 vision tokens
│ 包含剩余200 tokens │
└──────────────────────┘
总计:512 vision tokens 表示 1000 text tokens
压缩比:1000 / 512 ≈ 2×
💎 核心优势总结
1. 突破上下文限制
传统方法:
128K window → 只能处理 128K tokens
Glyph方法:
128K window → 可以处理 384K-512K tokens(3-4×)
极限压缩(8×):
128K window → 理论可处理 1M tokens!
2. 速度与成本优化
计算复杂度对比:
传统LLM(处理240K tokens):
├─ Attention: O(240K²) = 57.6B operations
├─ Memory: 240K × hidden_dim × num_layers
└─ 成本:巨大
Glyph(视觉表示80K tokens):
├─ Attention: O(80K²) = 6.4B operations ← 9× 更快
├─ Memory: 80K × hidden_dim × num_layers ← 3× 更小
└─ 成本:显著降低
3. 可测试时扩展
# 神奇的特性:推理时可以调节压缩比!
# 低延迟模式(DPI=72)
fast_mode = render(text, dpi=72)
# 压缩比: 4×, 准确率: 72%
# 平衡模式(DPI=96)
balanced_mode = render(text, dpi=96)
# 压缩比: 2.2×, 准确率: 91%
# 高精度模式(DPI=120)
accurate_mode = render(text, dpi=120)
# 压缩比: 1.2×, 准确率: 95%
# 用户可以根据需求动态选择!
🚨 局限性(论文诚实承认)
1. 对渲染参数敏感
问题:
字体大小从9pt改到10pt → 准确率下降5%
DPI从72改到60 → 准确率骤降10%
原因:
模型在特定配置下训练,泛化能力有限
解决方向(论文未做):
训练"自适应渲染器",根据任务动态调整
2. UUID等罕见序列识别困难
传统LLM:
"a3f2-8b91-4c5d-9e17" ✅ 完美识别
Glyph:
"a3f2-8b91-4c5d-9e17" ❌ 可能识别为 "a3f2-8b9l-4cSd-9e17"
(1变成l, 5变成S)
原因:
视觉相似字符难以区分
3. 任务泛化能力弱
DeepSeek-OCR现象(论文也承认):
├─ OCR任务: 97% 准确率 ✅
├─ 文档理解: 优秀 ✅
└─ 推理任务: 相对弱 ⚠️
Glyph也存在类似问题:
├─ 长文本QA: 优秀
├─ 多跳推理: 可以
└─ 数学/代码: 未充分测试
🔮 未来方向(论文展望)
1. 自适应渲染
# 当前:固定配置
config = fixed_optimal_config
# 未来:任务感知渲染
def adaptive_render(text, task_type):
if task_type == "速度敏感":
return render(text, dpi=60, compression=5×)
elif task_type == "准确率优先":
return render(text, dpi=120, compression=1.5×)
elif task_type == "代码":
return render(text, font="Monospace", style="code")
else:
return render(text, **auto_optimize(task_type))
2. 从128K扩展到10M
论文实验:
128K window + 8× compression = 处理1M tokens ✅
理论极限:
128K window + 80× compression = 处理10M tokens?
挑战:
├─ 信息损失(80×太极端)
├─ OCR精度(字会糊成一团)
└─ 推理能力(太长的链条)
可能的解决方案:
分层渲染(类似图像金字塔)
3. 混合架构
def hybrid_context_manager(context):
recent_context = context[-10K:] # 最近内容
old_context = context[:-10K] # 历史内容
# 最近内容:保持文本形式(高精度)
recent_tokens = tokenizer(recent_context)
# 历史内容:渲染压缩(高效率)
old_images = render_and_compress(old_context, ratio=4×)
# 混合输入
return combine(old_images, recent_tokens)
# 优势:
# ✅ 保留关键信息的精度
# ✅ 压缩不太重要的历史
# ✅ 平衡性能和效率
📝 最终总结:一个形象比喻
传统LLM = 一个字一个字读书的人
├─ 优点:一字不漏
├─ 缺点:慢,容易忘记前文
└─ 能力:最多读个几万字就累了
Glyph = 会速读和图像记忆的人
├─ 方法:把书"拍照"存进大脑
├─ 优点:快,记得住,能处理长书
├─ 缺点:偶尔会把"0"看成"O"
└─ 能力:能读几十万字的小说
核心思想:
用"空间"(图像)代替"时间"(逐字序列),
实现更高效的信息编码。
最精炼的一句话总结:
Glyph把"逐字读书"变成了"看书照片",用VLM的视觉理解能力实现3-4×文本压缩,让128K窗口的模型能处理384-512K tokens的长文本,同时保持准确率并大幅提升速度。
839

被折叠的 条评论
为什么被折叠?



