文本比较与合并,免费

粘贴两个版本的文本,逐行对比并以颜色显示差异。

比较结果

粘贴两段文本并点击「比较」。

工作原理

  1. 粘贴两段文本:在左侧面板输入原文,在右侧输入修订后的文本。
  2. 查看差异:修改的行会高亮显示 · 绿色表示新增,红色表示删除,黄色表示修改。
  3. 查看差异:滚动浏览彩色编码的差异结果,并复制或截图您需要的部分。

Diff 简史

现代文本 diff 始于贝尔实验室。Douglas McIlroy(同一位发明了 Unix 管道的 McIlroy)和 James W. Hunt 在 1970 年代初编写了最初的 Unix diff;它作为 Unix 第 5 版的一部分在 1974 年发布。算法被记录在贝尔实验室计算科学技术报告第 41 号(1976 年 6 月),一份题为「An Algorithm for Differential File Comparison」的内部报告中。Hunt-McIlroy 算法建立在最长公共子序列(LCS)问题之上,找出按顺序出现在两个输入中的最长行序列,而不在该序列中的所有内容要么是删除,要么是插入。十年后,Eugene W. MyersAlgorithmica 第 1 卷第 2 期(1986)上发表了 「An O(ND) Difference Algorithm and Its Variations」。Myers 将该问题重新表述为「编辑图」上的最短路径查找,并表明它可以在 O(ND) 时间和空间内求解,其中 N 是输入大小,D 是最小编辑脚本的大小。对于典型输入,即仅在少数地方不同的文件,D 很小,因此该算法在实践中很快。Myers 的论文成为了一个更快的 Unix diff 实现的基础,该实现比其前身快两到四倍,并产生更高质量的输出。Patience diff(Bram Cohen,2008)是一种 LCS 改进,它优先考虑唯一锚定行,在移动块周围产生更可读的 diff。git diff 中目前的默认值是 LibXDiff 中的直方图算法,通常被认为比普通 Myers 更快,在存在移动块时产生更可读的 diff(它在 2.11 中成为 Git 的默认值,2016 年 11 月 29 日发布)。数学基础走得更深:Levenshtein 距离(Vladimir Levenshtein,1965)是 LCS 问题的字符级表亲,而 Wagner-Fischer 动态规划解法(1974)是每个「模糊匹配」库仍然在内部实现的内容。

Diff 如何渲染

显示 diff 有四种常见的视觉惯例。并排,两列,左侧是原始,右侧是修改后,对应的行对齐。适合一目了然的比较;在桌面宽度下效果良好,但在窄移动视口上变得不可读。内联统一 diff,单列显示删除的行(通常以 - 为前缀并染成红色)、添加的行(+,绿色)和未更改的上下文行(无前缀,纯文本)。git diff 默认使用的布局。在移动设备上扩展性好,但失去了并排的空间并行性。单词级 diff,仅在更改的行内突出显示已更改的单词。对于大部分文本未更改但特定短语已编辑的散文比较很有用。字符级 diff,单独突出显示每个更改的字符。对于非常小的更改(打字错误纠正、单个数字编辑)很有用,其中单词级会突出显示整个单词。颜色惯例在整个生态系统中非常一致:添加用绿色,删除用红色,更改的值用黄色或琥珀色,未更改用中性灰色或无样式。此工具使用内联统一样式,在更改的行内进行字符级突出显示,这是一种混合,在移动设备上扩展性好,同时保留了散文编辑的字符级比较的精度。

三向合并,当两个 diff 需要组合时

双向 diff(此工具)告诉你版本 A 和版本 B 之间发生了什么变化。三向合并回答了一个更难的问题:给定一个共同祖先和两个分歧的修订版本,什么是合并的结果,它合并了两组更改?这是每个版本控制系统的核心操作,当两个开发人员独立编辑同一文件,其中一人尝试合并他们的工作时,系统需要将两个 diff 应用于原始文件。Khanna、Kunal 和 Pierce(2007)正式化的 diff3 算法是基础。Git 在自动合并失败时插入文件的七字符冲突标记惯例,<<<<<<<=======>>>>>>>,直接来自这一血统。现代视觉合并工具(VS Code 的三窗格合并编辑器,自 2022 年 6 月的 1.69 起默认启用;Scooter Software 的 Beyond Compare,自 1996 年起;Meld;Black Pixel 用于 macOS 的 Kaleidoscope)通过并排渲染所有三个版本以及第四个窗格用于提议的合并结果来处理三向合并。此工具专注于双向比较,三向合并属于真正的版本控制工作流。

常见用例

2026 年的 Diff 生态系统

除了 git diff 和 Unix diff 之外,几个专业 diff 工具值得一提。Beyond Compare(Scooter Software,1996)是长期存在的商业文件夹和文件比较工具,在开发人员和 IT 专业人员中流行用于跨机器 diff。Meld(开源,基于 GTK)是 GNOME 的默认值。Kaleidoscope(Black Pixel,macOS)与版本控制集成,是许多 Mac 开发人员的事实选择。VS Code 内置的 diff 编辑器原生处理双向和三向比较;三窗格合并编辑器在 1.69(2022 年 6 月)中变为默认启用。Mergely(Wayne Stidolph,2013,MIT 许可)是基于 CodeMirror 构建的规范浏览器双向合并编辑器。jsdiff(Kevin Decker,约 2010)是主导的 JavaScript diff 库,被你曾经粘贴过的每个基于浏览器的 diff 工具使用。diff-match-patch(Google 的 Neil Fraser,2006)是替代库,在单个 API 中处理 diff、模糊匹配和补丁生成;用于 Google 文档修订历史。Diffchecker 是主导的免费增值在线 diff 服务,功能齐全但隐私设有付费墙(免费层将文本发送到他们的服务器)。text-compare.com 是网上运行时间最长的纯文本 diff 站点,UI 过时但功能正常。

隐私:为什么仅浏览器在这里尤其重要

每个 diff 都精确揭示了两个版本之间发生了什么变化,而变化的内容通常比任何一个版本本身都更敏感。三个具体场景中这一点至关重要。安全补丁:diff 函数的易受攻击版本与修补版本,揭示了安全 bug 的精确位置和性质,找到补丁的攻击者可以为未修补版本制作漏洞利用(由 Tian 等人在 USENIX Security 2017 上记录的「patch gap」攻击)。将安全补丁粘贴到服务器端 diff 工具中本质上就是发布漏洞。合同谈判:diff 合同的两个版本,精确揭示了每一方关心的条款,这正是你不希望另一方(或任何观察网络的人)在谈判期间拥有的信息。出版前编辑决策:diff 编辑前后的手稿,揭示了作者和编辑决定剪掉或更改的内容,通常比最终出版的版本更具揭示性。服务器端 diff 工具将两个版本上传到第三方,在那里它们留在日志中。此工具完全通过 JavaScript 在你的浏览器中运行,在单击比较时在 DevTools 的 Network 标签中验证,或在页面加载后将其离线(飞行模式),工具仍然工作。

常见问题

可以比较代码文件吗?

可以。粘贴任意文本,包括代码、JSON、HTML、Markdown 或纯文本。diff 是纯文本的,适用于任何格式。

它会忽略空白差异吗?

启用「忽略空白」选项可跳过仅是空格或换行的差异。适合比较经过重新格式化但实际内容未改动的代码。

这使用什么算法?

Myers 的 O(ND) 算法(Eugene Myers,Algorithmica 第 1 卷第 2 号,1986),GNU diff 几十年来默认使用的相同算法,也是大多数文本 diff 实现的基础。Myers 将最长公共子序列问题重新表述为编辑图上的最短路径查找,使其在仅在少数地方不同的输入上实践中很快。较新的直方图算法(Git 自 v2.11(2016 年 11 月)起的当前默认值)在处理移动块方面稍好,但对于此工具处理的典型双粘贴用例来说是过度的。

有大小限制吗?

没有硬限制,但比较通过 JavaScript 在你的浏览器中运行,因此实际上限是你设备的可用内存。数万行可以舒适地工作。非常大的输入(数 MB 的日志文件、整本小说)会运行,但渲染可能需要明显的几秒钟。对于真正巨大的输入,使用 Git 命令行上的 diff,它流式输出,处理任意大小的文件而没有内存压力。

它可以进行三向合并或应用补丁吗?

目前不能,此工具专注于双向比较(A 与 B)。三向合并(带有冲突标记 <<<<<<< / ======= / >>>>>>>diff3 算法)是 Git 在合并分支时使用的操作;它需要一个共同祖先加上两个分歧的版本。对于三向合并,使用真正的版本控制系统或专用工具,如 VS Code 的三窗格合并编辑器(自 2022 年 6 月的 1.69 起默认启用)。

我的文本会被上传吗?

不会。比较完全通过 JavaScript 在你的浏览器中运行。你粘贴的文本永远不会越过网络,在单击比较时在 DevTools 的 Network 标签中验证,或在页面加载后将其离线(飞行模式),工具仍然工作。对于 diff 安全补丁(其中 diff 本身揭示了漏洞)、合同修订(其中 diff 揭示了谈判立场)或出版前编辑草稿尤其安全。

相关工具

差异检查器,免费 HTML 表格生成器,免费 行排序,免费 空白与文本清理器,免费