移动文件的 Git merge

标签 git github

我 fork 了一个 repo 并更改了文件 A。现在上游 repo 中的文件 A 已移动到子目录。我正在尝试将上游 repo merge 到我的 fork 上。

Git 认为文件 A 在其原始位置被删除,并在新的子目录中创建了一个新文件(这也可能是因为他们将文件向上游移动的方式)。

我想在新位置对这个文件进行修改,尽可能减少影响,w.r.t 提交历史和其他东西。谁能帮我解决这个问题?

最佳答案

Git 总是通过比较有问题的两棵树(或一棵树和索引,对于不包括 git merge 本身的情况)“事后”检测重命名。 (Linus Torvalds 认为这是一个特性;例如参见 this SO question。)

在任何情况下,git merge 都会运行 git 的内部 diff,并启用 merge 检测和默认的相似度指数 50%,除非您另外配置它​​。1 类似地, git diff 有一些默认值也是可配置的。如果您在 merge 基础和上游之间手动运行 git diff --find-renames -M50%,您可能没问题(但请参阅关于配置的脚注 1)。

如果 git 没有检测到重命名,您可能需要调整重命名检测阈值和/或增加 git 应该考虑的文件数量。其中第一个是 -X 选项中的 rename-threshold 值(rename-threshold 首次出现在 git 1.7.4 中)。参见 the documentation了解详情。


1您可以将 merge.renameLimit 设置为在重命名检测方面要考虑的文件数。如果您不设置它,当前默认值为 1000 个文件(但默认值已随时间变化)。此外,如果您不设置它,merge 将使用 diff.renameLimit,因此您可以只设置其中的第二个,并且 diff 和 merge 都使用这两个值。

文件重命名检测的工作方式有点复杂,但足够简单,可以通过示例进行描述。假设 git 正在比较提交 12345 和提交 67890,并且在 12345 中有路径名为 A 的文件,B/C, and D;但在 67890 中有路径名 B/gronkB/CD。这意味着路径 A 消失了,但新路径 B/gronk 出现了。然后 Git 会记住这些路径(直到重命名限制值),并将 12345:A 的内容与 67890:B/gronk 的内容进行比较。如果文件“足够相似”,git 将声明 12345:A 已重命名为 67890:B/gronk

我不确定 git 是如何确定一个文件是 50%、75% 或其他相似/不同的。不过,我已经看到相似性指数是基于“ block ”而不是行(即使通常的 diff 输出是面向行的)。

关于移动文件的 Git merge ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33269861/

相关文章:

xml - 在 git 中 merge XML 文件更改

node.js - 作为生成 Node 进程启动时显示来自 GIt 的反馈

github - Heroku app-setups api 无法与私有(private) git 存储库一起使用

GitHub - 如何直观地查看两个分支之间的文件差异?

用于创建文件的 GitHub API

git - 我可以使用 keybase.io 签署 git 提交吗?

公司代理背后的 Git 克隆

git - 将 BitBucket 中的 hg 存储库 fork 到 GitHub 存储库中

c - 指定下载目录

github - 如何为内部服务器的 Jenkins 配置 GitHub Webhook?