<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>墨迹</title>
    <link>https://blog.yugali.cn</link>
    <atom:link href="https://blog.yugali.cn/feed.xml" rel="self" type="application/rss+xml"/>
    <description>把读过的书、写过的代码、走过的路，誊在同一张稿纸上。</description>
    <language>zh-CN</language>
    <lastBuildDate>Fri, 18 Sep 2026 04:00:00 GMT</lastBuildDate>
    <item>
      <title>镰仓的一天：图文与视频的写法示例</title>
      <link>https://blog.yugali.cn/blog/kanagawa-day</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/kanagawa-day</guid>
      <pubDate>Fri, 18 Sep 2026 04:00:00 GMT</pubDate>
      <description>这篇笔记演示旅行内容的全部写法：本地图片、点开放大的灯箱、网格图集、页内直接播放的 B 站与直链视频。</description>
      <content:encoded><![CDATA[<p>这篇笔记演示旅行内容的全部写法：本地图片、点开放大的灯箱、网格图集、页内直接播放的 B 站与直链视频。</p><p>去了一趟镰仓。这篇同时是「图文写法示例」：正文图片、图集、视频的语法都在里面，照着抄就行。 正文插图 把照片放进 public/images/kanagawa/，然后一行 Markdown： 图片点击可以放大，全屏状态下支持缩放、键盘左右键切换本文里的所有图片。 本地图片在构建时会读取真实尺寸，加载过程不会把文字挤得跳来跳去。 图集 照片多的时候用图集语法，一段网格铺开，不占半屏正文： :::gallery{title="这一天的三个片段"} /images/kanagawa/sea.svg, /images/kanagawa/street.svg, /images/kanagawa/cafe.svg 同样点击进灯箱浏览。 视频 B 站或 YouTube：把视频页地址单独成一行贴进来，自动变成页内播放器： https://www.bilibili.com/video/BV1GJ411x7h7 直链视频（mp4 等，可以放在对象存储或任何能直连的地方）写法相同： https://mdn.github.io/shared-assets/videos/flower.mp4 播放器右下角有「在原页打开」。如果某处只想放一个普通链接、不要播放器，给链接加个名字即可，比如 花的教学视频。 收尾 下午的咖啡： 以上。照片视频都很少的时候，这种写法最省心；素材多了再考虑相册页。</p>]]></content:encoded>
      <category>旅行</category>
      <category>博客</category>
    </item>
    <item>
      <title>和 AI 一起写作，还是让 AI 替你写作</title>
      <link>https://blog.yugali.cn/blog/writing-with-ai</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/writing-with-ai</guid>
      <pubDate>Sat, 12 Sep 2026 04:00:00 GMT</pubDate>
      <description>用了大半年 AI 之后，我把它在写作里的位置从作者降到了编辑，这篇讲为什么。</description>
      <content:encoded><![CDATA[<p>用了大半年 AI 之后，我把它在写作里的位置从作者降到了编辑，这篇讲为什么。</p><p>用 AI 辅助写东西大半年了，结论先放在这里：AI 是一个极好的编辑，一个危险的作者。 危险的部分 让 AI 替我写一篇文章，产出通常通顺、周全、四平八稳，并且毫无痕迹感。问题就在这里：读完之后什么也留不下。 一篇值得读的文字需要一个「想不清楚的过程」。我在 与墨迹的第一次见面 里说，誊写是最好的复习，很多「我以为我懂了」都是在誊写时露馅的。这个露馅的瞬间是写作的核心价值，而 AI 的产出里没有这个过程，它直接给你一份「已经懂了」的成品。 成品很光滑，光滑到没有可以抓住的地方。 好用的部分 但我没有放弃它。现在的分工是这样的： 1. 我自己写初稿，允许烂 2. 让 AI 做读者，指出哪里没看懂、哪里跳跃了 3. 让它检查错别字和标点 4. 结构性的修改和所有取舍，回到我自己手上 第 2 步最有价值。以前找一个愿意逐字读你烂初稿的人很难，现在随时有一个不知疲倦的读者，还会礼貌地告诉你「这一段你的意思可能是 A 也可能是 B」。这种歧义指正，比它替我写的任何一段话都有用。 一个判断标准 要不要用 AI 参与？我现在的判断标准只有一条： 这件事的价值在于结果，还是在于过程。 结果导向的事（查语法、找资料、排版），放心交给它。过程导向的事（想清楚一个观点、记住一本书），亲手来。写作对我来说是过程导向的，所以初稿永远自己写。 这个标准也适用于别的行业，大概。</p>]]></content:encoded>
      <category>AI</category>
      <category>写作</category>
      <category>思考</category>
    </item>
    <item>
      <title>这个博客是怎么搭起来的：Next.js 与 Markdown</title>
      <link>https://blog.yugali.cn/blog/build-this-blog</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/build-this-blog</guid>
      <pubDate>Sat, 05 Sep 2026 04:00:00 GMT</pubDate>
      <description>从零搭一座个人博客的技术选型与实现：文件式 Markdown 内容、frontmatter 元信息、标签搜索，以及一套墨水配色的设计过程。</description>
      <content:encoded><![CDATA[<p>从零搭一座个人博客的技术选型与实现：文件式 Markdown 内容、frontmatter 元信息、标签搜索，以及一套墨水配色的设计过程。</p><p>决定重写博客之后，我给自己定了三个约束：内容必须是纯 Markdown 文件，样式要好看得有辨识度，标签和搜索要开箱即用。这篇文章记录实现的过程，也方便未来的自己翻修。 技术选型 需求 选择 理由 框架 Next.js App Router 静态生成，部署简单 样式 Tailwind CSS v4 写惯了 组件 shadcn/ui 源码进仓库，随便改 内容 content/posts/.md 纯文件，随时可以搬走 没有用 headless CMS，没有用数据库。一篇文章就是一个文件，frontmatter 写元信息： 内容加载 读取文件用 gray-matter 解析 frontmatter，渲染用 react-markdown 加上 GFM 插件和 rehype-highlight： 文章列表按日期倒序，标签在构建时聚合计数。因为都是静态生成，搜索干脆放在了浏览器端做：数据随页面下发，输入即过滤，不需要任何接口。 阅读时长的估算规则很粗糙但够用：中文按每分钟 350 字，英文按每分钟 200 词，两者相加取整。 设计 主题叫「蓝黑墨水与稿纸」。 颜色只有四个角色：冷调纸白做背景，蓝黑墨色做正文，钢笔靛蓝做唯一强调色，深黛色留给夜间模式。刻意避开了米色纸底配赤陶橘的常见组合，那套配色太眼熟了。 字体用霞鹜文楷做标题和正文，楷体的手写感贴合「稿纸」的隐喻；代码块用等宽字体。落地页的背景铺了一层极淡的方格，模拟稿纸的格子，标题末尾有一个缓慢闪烁的墨块光标，像正在落笔。 动效只有一处：首屏文字以「墨迹入纸」的方式浮现，一次播放即止，并且尊重系统的减弱动态设置。 还没做但想做的 RSS 订阅源 文章目录（TOC） 站内链接的引用计数 从读书笔记自动生成摘录卡 代码就在这个仓库里，感兴趣可以翻翻。</p>]]></content:encoded>
      <category>前端</category>
      <category>Next.js</category>
    </item>
    <item>
      <title>Markdown 能写出什么：一份完整的语法清单</title>
      <link>https://blog.yugali.cn/blog/markdown-guide</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/markdown-guide</guid>
      <pubDate>Tue, 01 Sep 2026 04:00:00 GMT</pubDate>
      <description>用一篇文章把常用 Markdown 语法全部演示一遍，同时也是这个博客渲染效果的自测页。</description>
      <content:encoded><![CDATA[<p>用一篇文章把常用 Markdown 语法全部演示一遍，同时也是这个博客渲染效果的自测页。</p><p>这篇文章本身就是一份测试数据：它把常用的 Markdown 语法全部用了一遍。如果你正在搭建自己的博客，可以直接把它抄走当渲染自测页。 行内元素 一段文字里可以有加粗、斜体、行内代码，以及一个链接。中英文混排的时候注意在两者之间留一个空格，比如 React 和 Vue，读起来会舒服很多。 列表 无序列表： 界面安静，注意力才能落在文字上 深色模式不是反色，是另一套配色 中文正文的行高要比英文松 有序列表： 1. 写作 2. 渲染 3. 发布 任务列表： [x] 搭好博客骨架 [x] 接入标签与搜索 [ ] 添加 RSS 订阅 引用 写作是为了思考，发布是为了确认自己思考过。 这句话是我自己说的，未必对。 代码块 一段 TypeScript： 一段 shell： 一段没有标注语言的代码，同样应该被善待： 表格 语法 用途 备注 # 标题 一篇文章只用一个一级标题 链接 外链在新标签页打开 > 引用 适合放金句，慎用 Mermaid 图表 技术文档里的流程图、时序图，直接写 mermaid 代码块，构建时渲染成静态 SVG（本地开发时同样即时可见）： 时序图也没问题： 视频 B 站、YouTube 或 mp4 直链，单独一行贴地址即自动内嵌播放器，写法见《镰仓的一天》示例文。 图片 分割线 到这里，一份语法清单就用完了。日常写作大概只用到其中的一半，但另一半决定了文章在细节处体不体面。</p>]]></content:encoded>
      <category>Markdown</category>
      <category>写作</category>
    </item>
    <item>
      <title>防抖与节流：写事件处理函数前先想清楚</title>
      <link>https://blog.yugali.cn/blog/debounce-throttle</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/debounce-throttle</guid>
      <pubDate>Fri, 28 Aug 2026 04:00:00 GMT</pubDate>
      <description>用输入框联想和滚动监听两个例子，把防抖与节流的区别讲清楚，附可以直接抄走的实现。</description>
      <content:encoded><![CDATA[<p>用输入框联想和滚动监听两个例子，把防抖与节流的区别讲清楚，附可以直接抄走的实现。</p><p>每次面试别人我都会问这两个概念，每次自己写滚动监听之前也都会重新想一遍。与其说是两个知识点，不如说是一道选择题：这个事件，你到底想响应多少次？ 问题是什么 浏览器里有些事件触发得非常勤快：输入框每敲一个键触发一次 input，滚动条每移动一像素都可能触发一次 scroll，鼠标在元素上每经过一个子节点触发一次 mousemove。 如果事件处理函数很重，比如每次都要发请求或者做大量计算，浏览器就会卡给你看。 解法有两个方向，取决于业务语义。 防抖：等你说完我再动 防抖（debounce）的语义是：停止触发 N 毫秒后，才真正执行。如果在这期间又触发了，就重新计时。 典型场景是搜索联想。用户想输入「防抖与节流」五个字，不应该每敲一个键就发一次请求： 用户连续输入时，请求永远不会发出；停顿超过 400 毫秒，才发最后那一次。五次请求合并成了一次。 节流：按固定节奏响应 节流（throttle）的语义是：不管触发多频繁，每 N 毫秒最多执行一次。 典型场景是滚动监听。页面滚动时想更新一个回到顶部的按钮显隐，用户的手不会停，但 UI 每 200 毫秒更新一次完全够用： 注意这是最简单的「 Leading edge」实现：先执行再计时。如果想要停止触发后再补一次，就得加上 trailing 逻辑，复杂度翻倍，多数场景不值得。 怎么选 一句话判断：关心最终状态用防抖，关心过程反馈用节流。 搜索联想、表单校验、窗口 resize 后重算布局：防抖 滚动加载、滚动吸顶、拖拽时的位置同步：节流 另外两个提醒。第一，addEventListener 的第三个参数传 passive: true，滚动场景能明显更顺滑。第二，组件卸载时记得移除监听并清掉定时器，不然防抖函数会在组件销毁后再执行一次。 就这些。下次写事件处理函数之前，先问一句：这个事件，我想响应多少次？</p>]]></content:encoded>
      <category>JavaScript</category>
      <category>前端</category>
    </item>
    <item>
      <title>与墨迹的第一次见面</title>
      <link>https://blog.yugali.cn/blog/hello-ink</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/hello-ink</guid>
      <pubDate>Thu, 20 Aug 2026 04:00:00 GMT</pubDate>
      <description>为什么要在 2026 年重新开始写博客，以及这个叫墨迹的地方打算存放些什么。</description>
      <content:encoded><![CDATA[<p>为什么要在 2026 年重新开始写博客，以及这个叫墨迹的地方打算存放些什么。</p><p>你好，这里是墨迹。 先交代一下动机。工作几年之后，我发现留在脑子里的东西越来越少：读过的文章转天就忘，踩过的坑修完就丢，想清楚的问题过两个月又要重新想一遍。笔记软件换了好几轮，收藏夹越来越长，但真正属于我自己的文字，几乎没有。 所以重新开始写。写得慢一点没关系，但要写完整：一篇笔记只讲一件事，讲到我明年再读的时候不需要翻参考资料也能看懂。 这里会写什么 大概是三类东西。 技术笔记。把工作里真正搞明白的问题誊写一遍，比如这次 搭起这个博客的过程。誊写是最好的复习，很多「我以为我懂了」都是在这个环节露馅的。 读书摘记。读的时候在书页边上乱画，读完之后挑值得的整理成一篇，像 夏天读完了三本书 这样。 随笔。生活里的一些时刻，不写下来就真的没有了。 为什么叫墨迹 取的是字面意思：墨水留下的痕迹。 博客里的每一篇文章都是一个 Markdown 文件，安静地躺在仓库里。它们是手写的痕迹，不是信息流里转瞬即逝的片段。哪天服务器关了，把这些文件拷走，墨迹还在。 纸上得来终觉浅，绝知此事要躬行。 陆游这两句诗是这座博客的座右铭。写下来只是第一步，做到才算数。 一些约定 对自己立的规矩，写在这里以便日后对照： 1. 每篇文章只讲一件事 2. 讲不明白的地方，说明自己还没弄懂 3. 不追热点，不留废话 以上。开始写吧。</p>]]></content:encoded>
      <category>随笔</category>
      <category>博客</category>
    </item>
    <item>
      <title>夏天读完了三本书</title>
      <link>https://blog.yugali.cn/blog/reading-notes-summer-2026</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/reading-notes-summer-2026</guid>
      <pubDate>Wed, 15 Jul 2026 04:00:00 GMT</pubDate>
      <description>七月到八月的读书摘记：《夜航西飞》《代码大全》选读，以及一本意料之外的小书。</description>
      <content:encoded><![CDATA[<p>七月到八月的读书摘记：《夜航西飞》《代码大全》选读，以及一本意料之外的小书。</p><p>夏天太热，周末下午不适合写代码，适合读书。三个月读完了三本，摘一点在这里。 夜航西飞 柏瑞尔·马卡姆在肯尼亚当飞行员的故事。最打动我的不是飞越大西洋的壮举，而是她写训练赛马和巡逻农场的段落：一个人对职业的熟练与忠诚，可以安静到这个程度。 未来藏在迷雾中，叫人看来胆怯。但当你踏足其中，就会云开雾散。 这段话抄在了笔记本的第一页。写作和飞行一样，起飞之前永远看不清全程，飞起来才有下一片天空。 代码大全（第二版，选读） 大部头没有从头读到尾，挑了构建质量相关的几章重读。这本一九九三年的书对今天的仍然成立的部分，恰恰是最不涉及具体技术的部分： 变量名的长度应该与其作用域成正比 防御式编程的本质是「不信任自己的输入」 复杂度守恒：你在代码里省掉的思考，会在调试时加倍偿还 第三条是我自己总结的，但它显然是从书里某一段长出来的。 一本意料之外的小书 在旧书店随手买的《如何阅读一本书》，出版比我父母年纪还大。本以为是凑数的畅销书，结果检讨了自己的读法：我读非虚构的习惯是用眼睛扫过，遇到同意的观点就点头，遇到不同意的就跳过。作者说这不叫阅读，这叫自我确认。 真正的阅读是被作者纠正的过程。合上书的时候，你应该和打开书之前不一样，哪怕只在一个很小的点上。 接下来 秋天想读两本长的：《基地》全七本，以及《计算机程序的构造和解释》。一个为了休息，一个为了补课。</p>]]></content:encoded>
      <category>读书</category>
      <category>随笔</category>
    </item>
    <item>
      <title>2025 年读过的五本书</title>
      <link>https://blog.yugali.cn/blog/2025-reading-list</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/2025-reading-list</guid>
      <pubDate>Wed, 03 Dec 2025 04:00:00 GMT</pubDate>
      <description>年终盘点：这一年里真正读完并且愿意推荐的五本书，各附一句实话。</description>
      <content:encoded><![CDATA[<p>年终盘点：这一年里真正读完并且愿意推荐的五本书，各附一句实话。</p><p>又是年底。翻记录，2025 年读完的书有十一本，其中翻到一半放下的有四本。按惯例挑五本值得推荐的写在这里，每本附一句实话。 程序员的修炼之道 老书第一次读。「不要重复发明轮子」人人都说，这本书讲的是更深的一层：什么时候应该造轮子。答案比想象中保守，大部分时候都不该。 失控 凯文·凯利的大部头，断断续续读了两个月。二十多年前的书，对蜂群思维和涌现的描述今天看依然新鲜，对预测的部分则要打个折扣。读它是为了看一个人如何把复杂系统讲清楚。 小王子 重读。第一次读是小时候，只记得玫瑰和狐狸。这次读出的是驯养与责任：你为你的玫瑰花费的时间，使你的玫瑰变得重要。写博客大概也是同一种驯养。 深入浅出统计学 给完全没基础的人补统计常识。例子啰嗦，但「假设检验」这一章讲得比教材清楚十倍。适合通勤路上翻。 长安的荔枝 「一骑红尘妃子笑」背后的物流工程。小吏办大事，处处是deadline。读完之后对需求文档里那句「这个需求很简单」有了新的理解。 明年 2026 年想少读一点，读慢一点。目标降到八本，每本写一篇完整的笔记，收在这里。</p>]]></content:encoded>
      <category>读书</category>
      <category>随笔</category>
    </item>
    <item>
      <title>第一次做代码评审，我学到的三件事</title>
      <link>https://blog.yugali.cn/blog/first-code-review</link>
      <guid isPermaLink="true">https://blog.yugali.cn/blog/first-code-review</guid>
      <pubDate>Wed, 18 Jun 2025 04:00:00 GMT</pubDate>
      <description>从被评审到评审别人的第一次转身：三件当时没人告诉我、现在想告诉当年的我的事。</description>
      <content:encoded><![CDATA[<p>从被评审到评审别人的第一次转身：三件当时没人告诉我、现在想告诉当年的我的事。</p><p>入职第三年，第一次以评审人的身份打开同事的合并请求。点开之前忽然意识到：以前都是别人看我，这次轮到我了。那天下午的评审做得磕磕绊绊，但有三件事当场就学会了。 先读测试，再读实现 一上来就读实现，很容易陷入对方的思路里，顺着他的逻辑走一遍，觉得哪里都对。先读测试，等于先看清楚这段代码承诺要做什么，再回头检查实现有没有兑现承诺。承诺和兑现之间的缝隙，就是问题所在。 评论的是代码，不是人 第一版评审意见里我写了「这里写错了」，发出去之前改成「这里和上面的分支重复了，可以合并吗」。前者是审判，后者是提问。事实描述加一个问号，对方的反应会完全不同。后来同事说，那次评审他改得很舒服，我想一半功劳在这个问号。 分清必须改和建议改 不是每条意见都值得阻塞合并。命名不优雅但能看懂，可以提，但标注「不阻塞」；边界条件漏了一种输入，必须拦下来。把火力留给真正要紧的事，评审才有公信力。样样都拦，最后就样样拦不住。 后记 这三件事没有一件是关于技术的，但我花了三年才明白：代码评审名义上评的是代码，实际上练的是沟通。</p>]]></content:encoded>
      <category>工作</category>
      <category>随笔</category>
    </item>
  </channel>
</rss>
