如何在git中合并具有不同目录层次结构的两个分支?

Posted

技术标签:

【中文标题】如何在git中合并具有不同目录层次结构的两个分支?【英文标题】:How to merge two branches with different directory hierarchies in git? 【发布时间】:2011-06-10 23:32:45 【问题描述】:

我开始将 Maven 与 Web 应用程序项目一起使用,因此目录层次结构发生了变化。我为 Maven 集成创建了一个新分支。现在我有两个分支,一个具有旧目录层次结构,一个具有 maven 目录层次结构。两个分支都有新的提交(错误修复和新功能)。

我想摆脱旧分支并将其更改合并到 Maven 分支。 Git 合并提供了无数感觉无法解决的冲突。我相信这是因为文件路径发生了变化。

处理这种合并的最佳方法是什么?

【问题讨论】:

让其他读者知道:这些问题的典型错误消息是too many files skipping inexact rename detection 【参考方案1】:

尝试将 merge.renameLimit 设置为较高的值以进行此合并。 git 会尝试检测重命名,但前提是文件数低于此限制,因为它需要 O(n^2) 处理时间:

git config merge.renameLimit 999999

完成后:

git config --unset merge.renameLimit

【讨论】:

注意,在增加 renameLimit 之后,我必须运行“git merge --abort”,这样我才能重试拉取。否则,这就成功了。【参考方案2】:

博文“Confluence, git, rename, merge oh my… ”添加了一些有趣的信息,说明了Robie 的answer(已投票):

当尝试检测重命名时,git 区分 精确和不精确的重命名

前者是重命名而不改变文件内容和 后者是可能包括更改文件内容的重命名(例如重命名/移动 Java 类)。

这个区别很重要,因为检测精确重命名的算法是线性的,并且总是会执行,而不精确重命名检测的算法是二次的(O(n^2)),如果更改的文件数超过了 git 不会尝试这样做某个阈值(默认为 1000)。

如果未明确设置,merge.renameLimit 默认为 1000 个文件,或者使用 diff.renameLimit 的值(如果已设置)。diff.renameLimit 影响 git diffgit showgit log,而 merge.renameLimit 仅适用于合并尝试(git mergegit cherry-pick)。

最好更改 merge.renameLimit 而不是更改 diff.renameLimit,这样 git 就不会在查看 git diff 输出等常见操作期间尝试查找重命名。

要显示重命名,git showgit log 等命令可以与启用重命名检测的 -M 选项一起使用。

Linus mentions:

是的,对于内核,我有

    [diff]
            renamelimit=0

完全禁用限制,因为默认限制确实非常低。 Git 非常擅长重命名检测。

但是,低默认值的原因并不是因为它不够灵活,而是因为它最终可能会使用大量内存(如果内存不足,交换将意味着它从“相当snappy" 到 "slow as molasses" - 但它仍然不会受到 CPU 的限制,它只是疯狂地分页)。

【讨论】:

以上是关于如何在git中合并具有不同目录层次结构的两个分支?的主要内容,如果未能解决你的问题,请参考以下文章

git 合并两个远程分支

为啥我在具有不同哈希的两个分支中有相同的提交

如何在 Git 中合并两个分支(主分支和演示分支)代码 [重复]

在 Git 中,如何在不挑选新分支的情况下对历史中具有多个合并提交的分支进行 rebase + squash

如何在 Git 的另一个分支中选择性地合并或选择更改?

Git不同项目代码分支合并,且仅合并特定提交