【发布时间】:2013-01-07 15:23:36
【问题描述】:
当我运行git add -p 时,git 有没有办法选择新制作的文件作为要选择的块??
所以如果我创建一个名为foo.java 的新文件,然后运行 git add -p,git 不会让我选择要添加到索引中的文件内容。
【问题讨论】:
当我运行git add -p 时,git 有没有办法选择新制作的文件作为要选择的块??
所以如果我创建一个名为foo.java 的新文件,然后运行 git add -p,git 不会让我选择要添加到索引中的文件内容。
【问题讨论】:
当我在新文件(未跟踪的文件)上尝试 git add -p someNewFile.txt 时,git 会简单地输出 No changes. 并停止。我必须告诉 git 我打算先跟踪新文件。
git add -N someNewFile.txt
git add -p
但是,由于该文件未被跟踪,它会显示为一个无法拆分的大块(因为它是全新的!)。所以,然后我需要将大块编辑成更小的位。如果您对此不熟悉,请查看this reference 以开始使用。
更新 - Hunk 编辑信息
我想更新它以防上述参考消失。因为新文件未被跟踪,git add -p 将文件中的每一行显示为一个大块中的新行。然后它会问你想用那个大块做什么,给你以下提示:
Stage this hunk [y,n,q,a,d,/,e,?]?
假设您不想提交整个块(因此,整个文件;因为我不确定在这种情况下您为什么要使用git add -p?),您将需要指定选项@987654328 @ 告诉 git 你想编辑大块。
一旦你告诉 git 你想编辑大块,它应该让你进入你选择的编辑器,这样你就可以进行更改。所有行都应该以 + 为前缀,并且 git 在文件末尾有一些解释性 cmets(以 # 为前缀)。只需在文件的初始提交中删除您不想要的任何行。然后保存并退出编辑器。
git对git的hunk选项的解释:
y - stage this hunk
n - do not stage this hunk
q - quit; do not stage this hunk or any of the remaining ones
a - stage this hunk and all later hunks in the file
d - do not stage this hunk or any of the later hunks in the file
g - select a hunk to go to
/ - search for a hunk matching the given regex
j - leave this hunk undecided, see next undecided hunk
J - leave this hunk undecided, see next hunk
k - leave this hunk undecided, see previous undecided hunk
K - leave this hunk undecided, see previous hunk
s - split the current hunk into smaller hunks
e - manually edit the current hunk
? - print help
【讨论】:
git add -N someNewFile.txt 后跟git add -p
git add -p filename 中的所有更改时(通过输入y),它退出时没有任何上演。当我尝试使用 e 进行编辑时,我收到“抱歉,无法编辑这个大块”
git push 说“一切都是最新的”之后这样做
还有一种非常相似的方法利用--cached 标志...
1) 将您未暂存的更改变为已暂存的更改,就像您添加的文件一样。
git add edited-file.txt
git add new-file.txt
git add directory-of-changes/
2) 查看差异(注意:您可以同时包含编辑文件和新文件)。
git diff --cached
3) 创建补丁。
git diff --cached > my_patch_file.patch
【讨论】:
git add -p 的一点是它不会添加所有内容,但让我挑选我想要添加的内容。此解决方案会盲目添加所有内容。
要包含每个新文件,您可以运行:
git add -N .
git add -p
如果你想经常使用它,你可以在你的~/.bashrc中创建一个别名:
alias gapan='git add --intent-to-add . && git add --patch'
N.B:如果你将它与一个空的新文件一起使用,git 将无法修补它并跳到下一个。
【讨论】:
git add -N 做什么的人,它只是将指定的未跟踪文件添加到索引中,但没有内容。
git add -p 真正的目的是为已跟踪的文件添加更改。
交互式选择要添加的文件的命令是git add -i。例如:
$ git add -i
*** Commands ***
1: status 2: update 3: revert 4: add untracked
5: patch 6: diff 7: quit 8: help
What now> a
1: another-new.java
2: new.java
Add untracked>> 2
1: another-new.java
* 2: new.java
Add untracked>>
added one path
*** Commands ***
1: status 2: update 3: revert 4: add untracked
5: patch 6: diff 7: quit 8: help
What now> q
Bye.
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)
new file: new.java
Untracked files:
(use "git add <file>..." to include in what will be committed)
another-new.java
(真正的命令有我无法在这里剪切和粘贴的颜色,所以它比看起来更好)
实际上,git add -i 的 patch 命令与git add -p 的作用相同,因此第二个是第一个的子集(尽管我承认我喜欢add -p 并且讨厌@ 987654327@我自己!)。
【讨论】:
No changes.。 OP 询问如何从新文件而不是整个文件中添加大块。我相信这里仍然需要--intent-to-add。
add -p 单独是行不通的,但这个答案建议add -i,确实如此。
git add -i。但是,您可以使用 git add -N 以非交互方式执行相同的操作。
Catshoes的回答包括:
当我在一个新文件(一个未跟踪的文件)上尝试
git add -p someNewFile.txt时,git 只会输出 No changes。然后停下来。
我必须告诉 git 我打算先跟踪新文件。
git add -N someNewFile.txt
git add -p
随着 Git 2.29(2020 年第四季度),这种情况应该会很快改变。
“git diff-files”的最新版本(man) 将“意图添加”路径的索引和工作树之间的差异显示为“新文件”补丁;
"git apply --cached"(man) 应该能够采用 "git diff-files" 并且应该作为路径的 "git add" 的等效项,但该命令未能这样做对于这样的路径。
参见Raymond E. Pasco (juped)@commit 4c025c6、commit e3cc41b(2020 年 8 月 8 日)和commit 7cfde3f(2020 年 8 月 6 日)。
(由 Junio C Hamano -- gitster -- 合并于 commit ca81676,8 月 17 日2020)
apply:允许在 i-t-a 条目上添加“新文件”补丁帮助:Junio C Hamano
签字人:Raymond E. Pasco
diff-files最近更改为将对索引中标记为“intent to add”的路径的更改视为新文件差异,而不是来自空 blob 的差异。但是,
apply拒绝在现有索引条目之上应用新的文件差异,除非是重命名。
这会导致使用 apply 的 "git add -p"(man) 在记录添加意图时尝试从文件暂存大块时失败。这会更改
check_to_create()中的逻辑,该逻辑以两种方式检查索引中是否已存在条目:
- 首先,如果
ok_if_exists为假,我们只搜索索引条目;- 其次,我们检查找到的任何索引条目上的
CE_INTENT_TO_ADD标志,如果已设置,则允许继续应用。
还有:
在 Git 2.29(2020 年第四季度)中,“add -p”现在允许编辑仅在意图中添加的路径。
参见Phillip Wood (phillipwood) 的commit 75a009d(2020 年 9 月 9 日)。
(由 Junio C Hamano -- gitster -- 合并于 commit 458205f,2020 年 9 月 22 日)
add -p: 修复意图添加路径的编辑签字人:Phillip Wood
报告人:Thomas Sullivan
报告人:Yuchen Ying
部分暂存新文件的一种流行方法是运行
git add -N <path>(man),然后使用git add -p的大块编辑(man) sup> 选择用户希望暂存的文件部分。由于85953a3187 ("diff-files --raw: 显示正确的意图添加文件的后图像", 2020-07-01, Git v2.28.0-rc0 -- merge 列在@ 987654346@) 这已停止工作,因为意图添加路径现在显示为新文件,而不是对空 blob 的更改,并且
git apply(man) 拒绝为标记为意图添加的路径。 7cfde3fa0f ("apply: allow "new file" patch on i-t-a entries", 2020-08-06) 修复了 apply 的问题,但仍然无法正确编辑添加的块。2c8bd8471a ("
checkout -p: 正确处理新文件", 2020-05-27, Git v2.28.0-rc0 -- merge 列在batch #2) 之前已将add -p更改为处理新文件文件,但它没有正确实现补丁编辑。
perl 版本简单地禁止编辑,而 C 版本打开编辑器时会显示完整的差异,而不是仅显示 hunk,这意味着用户必须手动编辑 hunk 标头才能使其工作。问题的根本原因是添加的文件将 diff 标头与大块数据一起存储,而不是像我们对其他更改所做的那样将两者分开。更改添加的文件以单独存储 diff 标头修复了编辑问题,但代价是必须进行特殊情况的空添加,因为它们不再具有与它们相关联的任何块,只有 diff 标头。
这些更改将一些现有代码移动到有条件的更改缩进中,最好使用
--color-moved-ws=allow-indentation-change(或--ignore-space-change可以很好地了解更改)
Git 2.32(2021 年第二季度)增加了一些清晰度:
参见 Peter Oliver (mavit) 的 commit 7a14acd(2021 年 4 月 27 日)。
(由 Junio C Hamano -- gitster -- 合并到 commit e60e9cc,2021 年 5 月 7 日)
doc: 指向补丁格式文档中的差异属性签字人:彼得·奥利弗
从使用 diff 相关命令生成补丁文本的文档中,请参阅 diff 属性的文档。
diff-generate-patch 现在包含在其man page 中:
- Hunk 标头提到了该hunk 所在的函数的名称 适用。请参阅“定义自定义块头”中的
gitattributes详细了解如何为此量身定制 特定语言。
【讨论】:
git add -N + git add -p 手动编辑帅哥
您可以使用git add --intent-to-add -p . 在一行中完成此操作
行为相同,但避免重复。
【讨论】: