惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

WordPress大学
WordPress大学
Engineering at Meta
Engineering at Meta
D
DataBreaches.Net
月光博客
月光博客
Recent Announcements
Recent Announcements
Google DeepMind News
Google DeepMind News
U
Unit 42
腾讯CDC
爱范儿
爱范儿
J
Java Code Geeks
有赞技术团队
有赞技术团队
Blog — PlanetScale
Blog — PlanetScale
N
Netflix TechBlog - Medium
B
Blog
Stack Overflow Blog
Stack Overflow Blog
GbyAI
GbyAI
T
The Blog of Author Tim Ferriss
小众软件
小众软件
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
Y
Y Combinator Blog
大猫的无限游戏
大猫的无限游戏
Microsoft Azure Blog
Microsoft Azure Blog
T
Tailwind CSS Blog
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知

est の 输入 输出和出入

海南之行后记 The httpx 1.0 situation Mimocode/Opencode 的 Responses API 支持 git fetch 实现断点续传 继续搓英汉双解词典v3 邮箱生态调研2026 “畜牲” 飞书并入豆包,文档是否减少? 从菲尔兹奖谈「包养」 iosevka字体让中文 ASCII diagram 图表对齐 为什么 Github OAuth 故意拦截 CORS gitweets改版,复刻微信「朋友圈」 MiMoCode 干完活儿发通知 写作能力和 locate cost grep vs sqlite 谁更适合微信聊天记录? [AI] curl -NT. 导致100% CPU原因 或许「数羊」真是个有效的入睡法 唯物主义「天命」论 我的 Vibe Coding 最佳实践——ADR文档 MacOS 快速插入当前时间 locate cost 基于 git 的零拷贝静态web服务器 AI和柜台费 Sutton 论 discovery Elon Musk 五步工作法 Playlet:DLNA听歌神器 免安装app播放NAS里的歌 不修改nginx接收websocket AI 硬伤 理解LLM的范式——它就是个差分机? 路径依赖
FSRS核心字段
est · 2026-05-17 · via est の 输入 输出和出入

无聊看了下 FSRS (Free Spaced Repetition Scheduler) ,想看它怎么存数据的

Card — 卡片当前状态

表结构:

字段 类型 说明
due Date 下次复习时间
stability float 记忆稳定性(R=90% 时的间隔天数)
difficulty float 难度,范围 [1, 10]
state int 状态机:New=0, Learning=1, Review=2, Relearning=3
learning_steps int 当前学习步骤 index
scheduled_days int 本次调度天数
reps int 总复习次数
lapses int 遗忘次数
last_review Date? 上次复习时间

核心字段详解

1. state

状态机,取值

  • New=0
  • Learning=1
  • Review=2
  • Relearning=3
         Again          Good/Hard/Easy
New ──────────→ Learning ──────────────→ Review
                  ↑  │                      │
                  │  │ Again (learning步内)  │
                  │  └──────────────────────┘
                  │                           │
                  │      Again (遗忘)         │
                  └─────── Relearning ←──────┘

state 决定调度公式分支,不能从 stability/difficulty 推导。同一个 stability/difficulty 的卡片,Review 和 Relearning 走完全不同的公式。

2. learning_steps

learning_steps 字段记录的是当前走到第几步(0-based index)。

新卡片第一次看到时,你不可能直接让它 10 天后再复习。所以先用预设的短间隔反复巩固:

默认 learning_steps = ['1m', '10m']

  • 第1次看 → 1分钟后复习
  • 第2次看 → 10分钟后复习
  • 第3次看 → 毕业,进入 Review,走 FSRS 长期间隔(几天→几周→几月)

某些测试用例里能看到 ['1m', '10m', '30m', '1h', '6h', '12h']

New ──[首次复习]──→ Learning (step=0)
                        │
                    [Good]│→ Learning (step=1)
                        │       │
                    [Good]│→ Review (毕业,FSRS接管)
                        │
                    [Again]│→ 回到 step=0
Review ──[Again]──→ Relearning (step=0)
                        │
                    [Good]│→ Review (重新毕业)

3. difficulty

一般取值1-10

3.1 初始化(New 卡片首次复习)

init_difficulty(g: Grade): number {
  const d = w[4] - Math.exp((g - 1) * w[5]) + 1
  return clamp(roundTo(d, 8), 1, 10)
}

从 grade(1-4)计算初始难度。grade 越大(记得越好),难度越低。

3.2 更新(已有卡片复习)

next_difficulty(d: number, g: Grade): number {
  const delta_d = -w[6] * (g - 3)          // grade>3 降难度,grade<3 升难度
  const next_d = d + linear_damping(delta_d, d)  // 线性阻尼防止越界
  return clamp(mean_reversion(init_easy, next_d), 1, 10)  // 均值回归
}

从当前 difficulty 和 本次 grade 推算下一个 difficulty。
关键结论
difficulty 是纯计算值,只依赖
- 上一次的值
- 本次 grade(1-4)
- 权重参数 w4, w5, w6, w7

不需要额外存储输入参数。每次复习时算法读 difficulty → 算新的 → 写回去

4. last_review

上一次 review 时间

5. stability

FSRS的核心指标,是个 float,看定义

export const S_MIN = 0.001
export const S_MAX = 36500.0

极限精简字段

  • stability==0 默认 state=0。
  • step给四个值0,1,2,然后为3表示走review。也代替 state
  • difficulty 给 16 状态够了
  • fp16 拿来存 stability
  • 32bit 拿来存 due_at
  • 1byte 拿来存 due_days

FSRS 最终算 interval 时是 round(s * modifier) 取整到天

之前最先学习的,到期那一天就先复习

考虑到db检索的方便性,直接存 4byte due_at 代替 last_review,然后1byte due_days 用来反推 last_review

为什么 due_days 0-255 ?需要连续 Good 评分 7-8 次才能突破 256 天。要么你彻底记住,要么就忘干净了。无所谓了。

┌──────────┬───────────┬──────────────┐
│ 2 bit    │ 4 bit     │ 16 bit       │
│ step     │ difficulty│ stability    │
│ 0,1,2,3  │ 0-11→1-10 │ FP16         │
└──────────┴───────────┴──────────────┘

更新

实际上 due_days 都不用存

min(max_interval, max(1, round(stability * interval_modifier)))

直接可以 stability 反推。囧。突然有点领会FSRS精华在哪里了。它丫的其实没啥调度算法。

甚至都不是给每张卡训练一条曲线。就是用数据集训练一组全局参数 w,设定为标准遗忘曲线长什么样,然后每次复习后就去更新 stability difficulty,也就是说S D这两个参数去映射这个曲线。

值钱的是这个曲线。。