CVS合并算法
合并两个分支(使用 -j)时 CVS 使用什么算法?
- CVS 标记、分支或日期是否可识别?
- 它只是进行纯文本比较(例如,使用 unix diff 工具)吗?
- 它使用 2 路还是 3 路差异?
- 如果它使用 3 路 diff,它使用的基本版本是什么?
谢谢
What algorithm does CVS use when merging two branches (using the -j)?
- Is the CVS tag, branch, or date aware?
- Does it just do a plain text diff (for example, using the unix diff tool)?
- Does it use a 2 way or 3 way diff?
- If it uses a 3 way diff, what is the base version it uses?
Thanks
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
记得前一阵子读到CVS merge其实是使用diff3算法来进行合并的。
此 PDF 文章 对 Diff3 的正式调查,作者:Sanjeev Khanna、Keshav Kunal ,以及宾夕法尼亚大学的 Benjamin C. Pierce 详细描述了 diff3 算法。
如果主要关注合并算法本身的属性,而不是它如何与 CVS 集成。
回答您的问题:
标签、日期意识
来自 CVS 手册页:
2 或 3 方式中,并且文本/二进制感知
diff3 默认为纯文本差异。它比较(差异)文件的 3 个版本。
来自 diff3 手册页:
比较期间的基本版本
根据链接的文章,基本版本是文件的两个当前版本(A 和 B)之间的最后一个通用版本 (O)。它首先使用2路diff算法来找到O和A、O和B之间的最长公共子序列。
然后(引自文章)它:
I remember a reading a while ago that CVS merge actually uses the diff3 algorithm to perform merging.
This PDF article A Formal Investigation of Diff3, by Sanjeev Khanna, Keshav Kunal, and Benjamin C. Pierce from the Universtiy of Pennsylvania describes the diff3 algorithm in detail.
If focuses primarily on the properties of the merging algorithm itself, not on how it integrates with CVS.
In answer to your questions:
Tag, date awareness
From the CVS man page:
2 or 3 way and text/binary awareness
diff3 defaults to a plain text diff. It compares (diffs) 3 versions of the file.
From the diff3 man page:
Base version during comparison
The base version, according to the linked article, is the last common version (O) between the two current versions of the file (A and B). It first uses the 2 way diff algorithm to find the longest common subsequences between O and A, and O and B.
Then (quoted from the article) it:
您可以使用两种不同形式的“合并”命令,它们执行的操作略有不同:
cvs up -j TAG
cvs up -j TAG1 -j TAG2
区别变体之间是选择“基本”修订版的方式,但任一变体的基本算法是,对于每个文件,CVS 选择的两个修订版之间的差异将应用到当前工作副本之上。
在第一种形式中,合并基础是给定标签和工作副本修订版的共同祖先。因此,假设您的本地修订版是 1.38(HEAD 上的修订版 #38),并且您要合并 1.34.4.2(HEAD 上的修订版 #34 的分支 4 上的修订版 2) - 共同祖先将是 1.34。我相信这个变体使用两个差异 1.34..1.38 和 1.34..1.34.4.2 进行三向合并,在它们不匹配的地方产生冲突。
在第二种形式中,您自己指定基本修订版,因此最终结果与 cvs diff -r TAG1 -r TAG2 | 大致相同。 patch 除了从 CVS 获取冲突标记之外。
There are two different forms of the "merge" command you can use, that do subtly different things:
cvs up -j TAG
cvs up -j TAG1 -j TAG2
The difference between the variants is how the "base" revision is selected, but the basic algorithm of either variant is that for each file, a diff between two revisions selected by CVS is applied on top of your current working copy.
In the first form, the merge base is the common ancestor of the given TAG and the working copy revision. So let's say your local revision is 1.38 (rev #38 on HEAD) and you're merging 1.34.4.2 (rev. 2 on branch 4 of rev #34 on HEAD) - the common ancestor will be 1.34. I believe this variant does a 3-way merge using the two diffs 1.34..1.38 and 1.34..1.34.4.2, producing conflicts where they mismatch.
In the second form, you're specifying the base revision yourself, so the end result is about the same as
cvs diff -r TAG1 -r TAG2 | patch
except for getting conflict markers from CVS.CVS
使用文件的三个修订版,将两个版本之间的差异合并到第三个版本中。除了签出的三个文件之外,实际合并不使用任何信息。您可以在CVS
源代码中查看详细信息。有问题的函数是src/rcscmds.c
中的RCS_merge
,它使用diff/diff3.c
中的call_diff3
(或类似的东西)。当然,您可以通过自己查找CVS
源来满足您的好奇心。The
CVS
uses three revisions of file merging the differences between the two into the third. The actual merge doesn't use any information besides the three files checked out. You can see the details inCVS
source code. The function in question isRCS_merge
insrc/rcscmds.c
, which usescall_diff3
fromdiff/diff3.c
(or something like that). You can, of course, satisfy your curiosity by looking upCVS
sources yourself.