设置和配置
获取和创建项目
基本快照
分支与合并
共享和更新项目
检查和比较
打补丁
调试
电子邮件
外部系统
服务器管理
指南
管理
底层命令
- 2.49.1 → 2.50.1 无更改
-
2.49.0
2025-03-14
- 2.48.1 → 2.48.2 无更改
-
2.48.0
2025-01-10
- 2.46.1 → 2.47.3 无更改
-
2.46.0
2024-07-29
- 2.45.4 无更改
-
2.45.3
2024-11-26
- 2.45.1 → 2.45.2 无更改
-
2.45.0
2024-04-29
- 2.44.1 → 2.44.4 无更改
-
2.44.0
2024-02-23
- 2.43.1 → 2.43.7 无更改
-
2.43.0
2023-11-20
- 2.42.2 → 2.42.4 无更改
-
2.42.1
2023-11-02
-
2.42.0
2023-08-21
- 2.41.1 → 2.41.3 无更改
-
2.41.0
2023-06-01
- 2.40.1 → 2.40.4 无更改
-
2.40.0
2023-03-12
- 2.36.1 → 2.39.5 无变更
-
2.36.0
2022-04-18
- 2.35.1 → 2.35.8 无更改
-
2.35.0
2022-01-24
- 2.33.3 → 2.34.8 无变更
-
2.33.2
2022-03-23
-
2.33.1
2021-10-12
-
2.33.0
2021-08-16
- 2.32.1 → 2.32.7 无变更
-
2.32.0
2021-06-06
- 2.31.1 → 2.31.8 无更改
-
2.31.0
2021-03-15
- 2.30.1 → 2.30.9 无更改
-
2.30.0
2020-12-27
- 2.29.1 → 2.29.3 无更改
-
2.29.0
2020-10-19
- 2.28.1 无更改
-
2.28.0
2020-07-27
- 2.27.1 无更改
-
2.27.0
2020-06-01
- 2.26.1 → 2.26.3 无更改
-
2.26.0
2020-03-22
- 2.25.2 → 2.25.5 无更改
-
2.25.1
2020-02-17
-
2.25.0
2020-01-13
- 2.24.1 → 2.24.4 无更改
-
2.24.0
2019-11-04
- 2.22.1 → 2.23.4 无更改
-
2.22.0
2019-06-07
- 2.21.1 → 2.21.4 无更改
-
2.21.0
2019-02-24
- 2.20.1 → 2.20.5 无更改
-
2.20.0
2018-12-09
- 2.19.1 → 2.19.6 无更改
-
2.19.0
2018-09-10
- 2.18.1 → 2.18.5 无更改
-
2.18.0
2018-06-21
- 2.17.1 → 2.17.6 无更改
-
2.17.0
2018-04-02
-
2.16.6
2019-12-06
-
2.15.4
2019-12-06
-
2.14.6
2019-12-06
-
2.13.7
2018-05-22
-
2.12.5
2017-09-22
-
2.11.4
2017-09-22
-
2.10.5
2017-09-22
-
2.9.5
2017-07-30
-
2.8.6
2017-07-30
- 2.7.6 无更改
-
2.6.7
2017-05-05
-
2.5.6
2017-05-05
-
2.4.12
2017-05-05
- 2.3.10 无更改
-
2.2.3
2015-09-04
-
2.1.4
2014-12-17
-
2.0.5
2014-12-17
描述
显示一个或多个对象(blob、tree、tag 和 commit)。
对于提交,它显示日志信息和文本差异。它还以 *git diff-tree --cc* 生成的特殊格式显示合并提交。
对于标签,它显示标签信息和引用的对象。
对于树,它显示名称(等同于带 --name-only 的 *git ls-tree*)。
对于普通 blob,它显示其原始内容。
可以利用 *git log* 命令理解的某些选项来控制提交引入的更改的显示方式。
本手册页仅描述最常用的选项。
选项
- <object>…
-
要显示的对象名称(默认为 *HEAD*)。有关拼写对象名称的更完整列表,请参阅 gitrevisions[7] 中的 “SPECIFYING REVISIONS” 部分。
- --pretty[=<format>]
- --format=<format>
-
以给定格式美化打印提交日志的内容,其中 *<format>* 可以是 *oneline*、*short*、*medium*、*full*、*fuller*、*reference*、*email*、*raw*、*format:<string>* 和 *tformat:<string>* 之一。当 *<format>* 不属于上述任何一种,并且其中包含 *%placeholder* 时,其行为等同于给定 *--pretty=tformat:<format>*。
有关每种格式的更多详细信息,请参阅“PRETTY FORMATS”部分。当 *=<format>* 部分省略时,默认为 *medium*。
注意:您可以在仓库配置中指定默认的美化格式(请参阅 git-config[1])。
- --abbrev-commit
-
显示一个唯一标识对象的短前缀,而不是完整的 40 字节十六进制提交对象名称。可以使用“--abbrev=<n>”选项(如果显示,它也会修改 diff 输出)来指定前缀的最小长度。
这应该能让使用 80 列终端的人更容易阅读“--pretty=oneline”。
- --no-abbrev-commit
-
显示完整的 40 字节十六进制提交对象名称。这会取消
--abbrev-commit
的效果,无论是显式指定还是由其他选项(如“--oneline”)隐含。它还会覆盖log.abbrevCommit
变量。 - --oneline
-
这是“--pretty=oneline --abbrev-commit”组合使用的简写。
- --encoding=<encoding>
-
提交对象在其编码头中记录了日志消息所使用的字符编码;此选项可用于告知命令以用户首选的编码重新编码提交日志消息。对于非底层命令,这默认为 UTF-8。请注意,如果一个对象声称以
X
编码,并且我们正在以X
输出,我们将按原样输出该对象;这意味着原始提交中的无效序列可能会被复制到输出中。同样,如果 iconv(3) 无法转换提交,我们将静默地按原样输出原始对象。 - --expand-tabs=<n>
- --expand-tabs
- --no-expand-tabs
-
在输出日志消息之前,执行制表符扩展(将每个制表符替换为足够的空格,以填充到下一个显示列,该列是 *<n>* 的倍数)。
--expand-tabs
是--expand-tabs=8
的简写,而--no-expand-tabs
是--expand-tabs=0
的简写,它禁用制表符扩展。默认情况下,制表符会在将日志消息缩进 4 个空格的漂亮格式(即默认的 *medium*、*full* 和 *fuller*)中进行扩展。
- --notes[=<ref>]
-
当显示提交日志信息时,显示批注提交的注释(参见 git-notes[1])。当命令行中没有给定
--pretty
、--format
或--oneline
选项时,这是git
log
、git
show
和git
whatchanged
命令的默认行为。默认情况下,显示的注释来自
core.notesRef
和notes.displayRef
变量中列出的注释引用(或相应的环境变量覆盖)。有关更多详细信息,请参阅 git-config[1]。使用可选的 *<ref>* 参数,使用该引用查找要显示的注释。当引用以
refs/notes/
开头时,它可以指定完整的引用名称;当它以notes/
开头时,以refs/
开头时,否则会加上refs/notes/
前缀以形成引用的完整名称。可以组合多个 --notes 选项来控制显示哪些注释。示例:“--notes=foo”将只显示“refs/notes/foo”中的注释;“--notes=foo --notes”将同时显示“refs/notes/foo”中的注释和默认注释引用中的注释。
- --no-notes
-
不显示注释。这会通过重置显示注释的注释引用列表来抵消上述
--notes
选项。选项按命令行中给定的顺序解析,因此例如“--notes --notes=foo --no-notes --notes=bar”将只显示“refs/notes/bar”中的注释。 - --show-notes-by-default
-
除非给出显示特定注释的选项,否则显示默认注释。
- --show-notes[=<ref>]
- --[no-]standard-notes
-
这些选项已弃用。请改用上面的 --notes/--no-notes 选项。
- --show-signature
-
通过将签名传递给
gpg
--verify
并显示输出,检查签名提交对象的有效性。
漂亮格式(PRETTY FORMATS)
如果提交是合并提交,并且漂亮格式不是 *oneline*、*email* 或 *raw*,则在 *Author:* 行之前会插入一行附加信息。此行以“Merge: ”开头,并打印祖先提交的哈希值,用空格分隔。请注意,如果限制了历史视图,则列出的提交不一定是**直接**父提交的列表:例如,如果您只对与特定目录或文件相关的更改感兴趣。
有几种内置格式,您可以通过将 pretty.<name> 配置选项设置为另一个格式名称或一个 *format:* 字符串来定义其他格式,如下所述(参见 git-config[1])。以下是内置格式的详细信息:
-
oneline
<hash> <title-line>
这旨在尽可能紧凑。
-
short
commit <hash> Author: <author>
<title-line>
-
medium
commit <hash> Author: <author> Date: <author-date>
<title-line>
<full-commit-message>
-
full
commit <hash> Author: <author> Commit: <committer>
<title-line>
<full-commit-message>
-
fuller
commit <hash> Author: <author> AuthorDate: <author-date> Commit: <committer> CommitDate: <committer-date>
<title-line>
<full-commit-message>
-
reference
<abbrev-hash> (<title-line>, <short-author-date>)
此格式用于在提交消息中引用另一个提交,它与
--pretty='format:%C
(auto
)%h
(%s,
%ad
) 相同。默认情况下,日期使用--date=short
格式化,除非明确指定了另一个--date
选项。与任何带有格式占位符的format:
一样,其输出不受--decorate
和--walk-reflogs
等其他选项的影响。 -
email
From <hash> <date> From: <author> Date: <author-date> Subject: [PATCH] <title-line>
<full-commit-message>
-
mboxrd
类似于 *email*,但提交消息中以“From ”开头(前面有零个或多个“>”)的行会用“>”引用,以免被误认为是新提交的开始。
-
raw
*raw* 格式精确显示提交对象中存储的整个提交。值得注意的是,无论是否使用 --abbrev 或 --no-abbrev,哈希值都会完整显示,并且 *parents* 信息显示真实的父提交,而不考虑嫁接或历史简化。请注意,此格式会影响提交的显示方式,但不会影响差异的显示方式,例如
git
log
--raw
。要在原始差异格式中获取完整的对象名称,请使用--no-abbrev
。 -
format:<format-string>
*format:<format-string>* 格式允许您指定要显示的信息。它的工作方式有点像 printf 格式,但值得注意的是,您使用 *%n* 而不是 *\n* 来获得换行符。
例如,*format:"The author of %h was %an, %ar%nThe title was >>%s<<%n"* 将显示类似以下内容
The author of fe6e0ee was Junio C Hamano, 23 hours ago The title was >>t4119: test autocomputing -p<n> for traditional diff input.<<
占位符为
-
扩展为单个字面字符的占位符
-
影响后续占位符格式的占位符
- %Cred
-
切换颜色为红色
- %Cgreen
-
切换颜色为绿色
- %Cblue
-
切换颜色为蓝色
- %Creset
-
重置颜色
- %C(…)
-
颜色规范,如 git-config[1] 的“CONFIGURATION FILE”部分中的“Values”所述。默认情况下,仅当为日志输出启用颜色时(通过
color.diff
、color.ui
或--color
,并遵循前者的auto
设置,如果我们输出到终端),才会显示颜色。%C
(auto,...
) 被接受作为默认值的历史同义词(例如,%C
(auto,red
))。指定%C
(always,...
) 将即使在颜色未启用时也显示颜色(但请考虑直接使用--color=always
来为整个输出启用颜色,包括此格式和 Git 可能着色的其他任何内容)。仅使用auto
(即%C
(auto
))将会在颜色再次切换之前,对下一个占位符启用自动着色。 - %m
-
左 (<)、右 (>) 或边界 (
-
) 标记 - %w([<w>[,<i1>[,<i2>]]])
-
切换行包裹,类似于 git-shortlog[1] 的 -w 选项。
- %<( <N> [,trunc|ltrunc|mtrunc])
-
使下一个占位符至少占用 N 列宽度,如有必要则在右侧填充空格。如果输出长于 N 列,可选地在左侧(ltrunc)
..ft
、中间(mtrunc)mi..le
或末尾(trunc)rig..
截断(带省略号 *..*)。注意 1:截断仅在 N >= 2 时才正确。注意 2:N 和 M 值(见下文)周围的空格是可选的。注意 3:表情符号和其他宽字符将占用两个显示列,这可能会超出列边界。注意 4:分解字符组合标记可能会在填充边界处错位。 - %<|( <M> )
-
使下一个占位符至少占据直到第 M 个显示列,如有必要则在右侧填充空格。使用负 M 值表示从终端窗口右侧边缘测量的列位置。
- %>( <N> ), %>|( <M> )
-
类似于 *%<( <N> )*、*%<|( <M> )*,但在左侧填充空格
- %>>( <N> ), %>>|( <M> )
-
类似于 *%>( <N> )*、*%>|( <M> )*,但如果下一个占位符占用比给定更多的空间,并且其左侧有空格,则使用这些空格
- %><( <N> ), %><|( <M> )
-
类似于 *%<( <N> )*、*%<|( <M> )*,但两侧都填充(即文本居中)
-
扩展为从提交中提取信息的占位符
- %H
-
提交哈希
- %h
-
缩写提交哈希
- %T
-
树哈希
- %t
-
缩写树哈希
- %P
-
父哈希
- %p
-
缩写父哈希
- %an
-
作者姓名
- %aN
-
作者姓名(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %ae
-
作者电子邮件
- %aE
-
作者电子邮件(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %al
-
作者电子邮件的本地部分(@ 符号之前的部分)
- %aL
-
作者电子邮件的本地部分(参见 *%al*),遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %ad
-
作者日期(格式遵循 --date= 选项)
- %aD
-
作者日期,RFC2822 样式
- %ar
-
作者日期,相对格式
- %at
-
作者日期,UNIX 时间戳
- %ai
-
作者日期,ISO 8601 类似格式
- %aI
-
作者日期,严格 ISO 8601 格式
- %as
-
作者日期,短格式 (
YYYY-MM-DD
) - %ah
-
作者日期,人类可读格式(类似于 git-rev-list[1] 的
--date=human
选项) - %cn
-
提交者姓名
- %cN
-
提交者姓名(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %ce
-
提交者电子邮件
- %cE
-
提交者电子邮件(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %cl
-
提交者电子邮件本地部分(@ 符号之前的部分)
- %cL
-
提交者电子邮件本地部分(参见 *%cl*),遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %cd
-
提交者日期(格式遵循 --date= 选项)
- %cD
-
提交者日期,RFC2822 样式
- %cr
-
提交者日期,相对格式
- %ct
-
提交者日期,UNIX 时间戳
- %ci
-
提交者日期,ISO 8601 类似格式
- %cI
-
提交者日期,严格 ISO 8601 格式
- %cs
-
提交者日期,短格式 (
YYYY-MM-DD
) - %ch
-
提交者日期,人类可读格式(类似于 git-rev-list[1] 的
--date=human
选项) - %d
-
引用名称,类似于 git-log[1] 的 --decorate 选项
- %D
-
不带“ (”和“)”包裹的引用名称。
- %(decorate[:<options>])
-
带有自定义装饰的引用名称。
decorate
字符串后面可以跟一个冒号和零个或多个逗号分隔的选项。选项值可以包含字面格式代码。由于逗号(%x2C
)和右括号(%x29
)在选项语法中的作用,必须使用它们。-
prefix=<value>:在引用名称列表之前显示。默认为“ (”。
-
suffix=<value>:在引用名称列表之后显示。默认为“)”。
-
separator=<value>:在引用名称之间显示。默认为“
,
”。 -
pointer=<value>:显示在 HEAD 和它指向的分支之间(如果有)。默认为“ -> ”。
-
tag=<value>:在标签名称之前显示。默认为“
tag:
”。
-
例如,要生成没有包装或标签注释的装饰,并使用空格作为分隔符
+
%
(decorate:prefix=,suffix=,tag=,separator=
)- %(describe[:<options>])
-
人类可读的名称,类似于 git-describe[1];对于无法描述的提交为空字符串。
describe
字符串后面可以跟一个冒号和零个或多个逗号分隔的选项。当同时添加或删除标签时,描述可能会不一致。-
tags[=<bool-value>]:除了考虑带注释的标签外,还考虑轻量级标签。
-
abbrev=<number>:不使用缩写对象名称的默认十六进制数字位数(将根据仓库中对象的数量而变化,默认为 7),而是使用 <number> 位数,或者所需尽可能多的位数以形成唯一的对象名称。
-
match=<pattern>:仅考虑与给定
glob
(7
) 模式匹配的标签,不包括“refs/tags/”前缀。 -
exclude=<pattern>:不考虑与给定
glob
(7
) 模式匹配的标签,不包括“refs/tags/”前缀。
-
- %S
-
命令行中给出用于到达提交的引用名称(类似于
git
log
--source
),仅适用于git
log
- %e
-
编码
- %s
-
主题
- %f
-
已清理的主题行,适合作为文件名
- %b
-
正文
- %B
-
原始正文(未包装的主题和正文)
- %N
-
提交注释
- %GG
-
GPG 对签名提交的原始验证消息
- %G?
-
对于有效签名显示“G”,对于无效签名显示“B”,对于有效但未知有效性的签名显示“U”,对于已过期但有效的签名显示“X”,对于由已过期密钥生成但有效的签名显示“Y”,对于由已撤销密钥生成但有效的签名显示“R”,如果无法检查签名(例如缺少密钥)显示“E”,如果没有签名显示“N”
- %GS
-
显示签名提交的签名者姓名
- %GK
-
显示用于签署签名提交的密钥
- %GF
-
显示用于签署签名提交的密钥的指纹
- %GP
-
显示用于签署签名提交的子密钥所属主密钥的指纹
- %GT
-
显示用于签署签名提交的密钥的信任级别
- %gD
-
reflog 选择器,例如
refs/stash@{1}
或refs/stash@{2
minutes
ago}
;格式遵循-g
选项的规则。@ 符号之前的部分是命令行中给出的引用名称(因此git
log
-g
refs/heads/master
将生成refs/heads/master@{0}
)。 - %gd
-
缩短的 reflog 选择器;与
%gD
相同,但为了人类可读性,引用名称部分被缩短(因此refs/heads/master
变为master
)。 - %gn
-
reflog 身份名称
- %gN
-
reflog 身份名称(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %ge
-
reflog 身份电子邮件
- %gE
-
reflog 身份电子邮件(遵循 .mailmap,参见 git-shortlog[1] 或 git-blame[1])
- %gs
-
reflog 主题
- %(trailers[:<options>])
-
显示由 git-interpret-trailers[1] 解析的正文末尾部分(trailers)。
trailers
字符串后面可以跟一个冒号和零个或多个逗号分隔的选项。如果任何选项被多次提供,则以最后一次出现为准。-
key=<key>:仅显示带有指定 <key> 的末尾部分。匹配不区分大小写,尾随冒号是可选的。如果多次给定此选项,则显示匹配任何键的末尾行。此选项自动启用
only
选项,以便隐藏末尾块中非末尾行。如果不需要此功能,可以使用only=false
禁用。例如,%
(trailers:key=Reviewed-by
) 显示键为Reviewed-by
的末尾行。 -
only[=<bool>]:选择是否应包含末尾块中非末尾行。
-
separator=<sep>:指定插入在末尾行之间的分隔符。默认为换行符。字符串 <sep> 可以包含上面描述的字面格式代码。要使用逗号作为分隔符,必须使用
%x2C
,否则它将被解析为下一个选项。例如,%
(trailers:key=Ticket,separator=%x2C
) 显示所有键为“Ticket”的末尾行,并用逗号和空格分隔。 -
unfold[=<bool>]:使其行为类似于给定 interpret-trailer 的
--unfold
选项。例如,%
(trailers:only,unfold=true
) 展开并显示所有末尾行。 -
keyonly[=<bool>]:仅显示末尾部分的键部分。
-
valueonly[=<bool>]:仅显示末尾部分的值部分。
-
key_value_separator=<sep>:指定插入在每个末尾部分的键和值之间的分隔符。默认为“: ”。否则,它与上面的 *separator=<sep>* 共享相同的语义。
-
-
注意
|
某些占位符可能取决于给定给修订遍历引擎的其他选项。例如,%g* reflog 选项将插入一个空字符串,除非我们正在遍历 reflog 条目(例如,通过 git log -g )。如果命令行上尚未提供 --decorate ,%d 和 %D 占位符将使用“short”装饰格式。 |
布尔选项接受一个可选值 [=
<bool-value>]。--type=bool
git-config[1] 接受的值,例如 yes
和 off
,都被接受。不带 =
<value> 给出布尔选项等同于带 =true
给出。
如果您在占位符的 *%* 后面添加 +
(加号),则仅当占位符扩展为非空字符串时,才会在扩展之前立即插入一个换行符。
如果您在占位符的 *%* 后面添加 -
(减号),则仅当占位符扩展为空字符串时,才会删除紧接在扩展之前的所有连续换行符。
如果您在占位符的 *%* 后面添加 ` `(空格),则仅当占位符扩展为非空字符串时,才会在扩展之前立即插入一个空格。
-
tformat
*tformat:* 格式的工作方式与 *format:* 完全相同,只是它提供的是“终止符”语义而非“分隔符”语义。换句话说,每个提交都会附加消息终止符字符(通常是换行符),而不是在条目之间放置分隔符。这意味着单行格式的最后一个条目将正确地以新行终止,就像“oneline”格式一样。例如:
$ git log -2 --pretty=format:%h 4da45bef \ | perl -pe '$_ .= " -- NO NEWLINE\n" unless /\n/' 4da45be 7134973 -- NO NEWLINE $ git log -2 --pretty=tformat:%h 4da45bef \ | perl -pe '$_ .= " -- NO NEWLINE\n" unless /\n/' 4da45be 7134973
此外,任何包含
%
的无法识别的字符串都会被解释为前面带有tformat:
。例如,以下两行是等效的:$ git log -2 --pretty=tformat:%h 4da45bef $ git log -2 --pretty=%h 4da45bef
差异格式(DIFF FORMATTING)
以下选项可用于更改 git
show
生成差异输出的方式。
-p
-u
--patch
-
生成补丁(参见 使用 -p 生成补丁文本)。
-s
--no-patch
-
抑制来自差异机制的所有输出。对于像
git
show
这样默认显示补丁的命令,它可用于抑制其输出,或者在别名中取消命令行中早期--patch
、--stat
等选项的效果。 - -m
-
以默认格式显示合并提交的差异。这类似于
--diff-merges=on
,不同之处在于,除非同时给出-p
,否则-m
不会产生任何输出。 - -c
-
为合并提交生成组合差异输出。是
--diff-merges=combined
-p
的快捷方式。 - --cc
-
为合并提交生成密集组合差异输出。是
--diff-merges=dense-combined
-p
的快捷方式。 - --dd
-
对于合并提交和常规提交,都生成与第一个父提交相关的差异。是
--diff-merges=first-parent
-p
的快捷方式。 - --remerge-diff
-
为合并提交生成重新合并差异输出。是
--diff-merges=remerge
-p
的快捷方式。 - --no-diff-merges
-
--diff-merges=off
的同义词。 - --diff-merges=<format>
-
指定用于合并提交的差异格式。默认是 `dense-combined`,除非使用了
--first-parent
,在这种情况下,默认是first-parent
。支持以下格式:
- off, none
-
禁用合并提交的差异输出。用于覆盖隐含值。
- on, m
-
使合并提交的差异输出以默认格式显示。默认格式可以使用
log.diffMerges
配置变量更改,其默认值为separate
。 - first-parent, 1
-
显示相对于第一个父提交的完整差异。这与
--patch
为非合并提交生成的格式相同。 - separate
-
显示相对于每个父提交的完整差异。为每个父提交生成单独的日志条目和差异。
- combined, c
-
同时显示每个父提交与合并结果之间的差异,而不是一次显示一个父提交与结果之间的配对差异。此外,它只列出从所有父提交中修改过的文件。
- dense-combined, cc
-
通过省略那些在父级中内容只有两种变体且合并结果未经修改地选取其中一种的无趣代码块,进一步压缩
--diff-merges=combined
产生的输出。 - remerge, r
-
重新合并两个父合并提交,以创建临时的树对象——可能包含带有冲突标记等的文件。然后显示该临时树与实际合并提交之间的差异。
使用此选项时发出的输出可能会发生变化,并且它与其他选项的交互方式也会发生变化(除非明确文档化)。
- --combined-all-paths
-
使组合差异(用于合并提交)列出所有父提交的文件名。因此,它仅在
--diff-merges=
[dense-
]combined
使用时才生效,并且可能仅在检测到文件名更改时有用(即当请求了重命名或复制检测时)。 -U
<n>--unified=
<n>-
生成包含 <n> 行上下文(而不是通常的三行)的 diff。隐含
--patch
。 --output=
<file>-
输出到特定文件而不是标准输出。
--output-indicator-new=
<char>--output-indicator-old=
<char>--output-indicator-context=
<char>-
指定用于指示生成补丁中新行、旧行或上下文行的字符。通常它们分别是
+
、-
和 ' '。 --raw
-
对于每个提交,使用原始差异格式显示更改摘要。请参阅 git-diff[1] 的“RAW OUTPUT FORMAT”部分。这与以原始格式显示日志本身不同,后者可以通过
--format=raw
实现。 --patch-with-raw
-
-p
--raw
的同义词。 -t
-
在差异输出中显示树对象。
--indent-heuristic
-
启用启发式算法,该算法会移动差异块边界,使补丁更易于阅读。这是默认设置。
--no-indent-heuristic
-
禁用缩进启发式算法。
--minimal
-
花费额外时间以确保生成最小的差异。
--patience
-
使用“patience diff”算法生成差异。
--histogram
-
使用“histogram diff”算法生成差异。
--anchored=
<text>-
使用“anchored diff”算法生成差异。
此选项可以多次指定。
如果一行在源和目标中都存在,只存在一次,并且以 <text> 开头,则此算法会尝试阻止其在输出中显示为删除或添加。它内部使用“patience diff”算法。
--diff-algorithm=
(patience
|minimal
|histogram
|myers
)-
选择一种差异算法。变体如下:
例如,如果您将
diff.algorithm
变量配置为非默认值,但希望使用默认值,则必须使用--diff-algorithm=default
选项。 --stat
[=
<width>[,
<name-width>[,
<count>]]]-
生成差异统计(diffstat)。默认情况下,文件名部分将占用所需的所有空间,其余部分用于图形部分。最大宽度默认为终端宽度,如果未连接到终端,则为 80 列,并且可以通过 *<width>* 覆盖。文件名部分的宽度可以通过在逗号后给出另一个宽度 *<name-width>* 或设置
diff.statNameWidth=
<name-width> 来限制。图形部分的宽度可以通过使用--stat-graph-width=
<graph-width> 或设置diff.statGraphWidth=
<graph-width> 来限制。使用--stat
或--stat-graph-width
会影响所有生成统计图的命令,而设置diff.statNameWidth
或diff.statGraphWidth
不会影响git
format-patch
。通过给出第三个参数 *<count>*,您可以将输出限制为前 *<count>* 行,如果还有更多行,则后面跟 ...。这些参数也可以通过
--stat-width=
<width>、--stat-name-width=
<name-width> 和--stat-count=
<count> 单独设置。 --compact-summary
-
输出扩展头部信息的精简摘要,例如文件创建或删除(“new”或“gone”,可选
+l
如果是符号链接)以及模式更改(+x
或-x
分别用于添加或移除可执行位)在 diffstat 中。该信息置于文件名部分和图形部分之间。隐含--stat
。 --numstat
-
类似于
--stat
,但以十进制表示法显示添加和删除的行数,并且不缩写路径名,以使其更具机器友好性。对于二进制文件,输出两个-
而不是显示0
0
。 --shortstat
-
仅输出
--stat
格式的最后一行,其中包含修改文件的总数,以及添加和删除的行数。 -X
[<param>,...
]--dirstat
[=
<param>,...
]-
输出每个子目录中更改的相对数量分布。可以通过传递逗号分隔的参数列表来自定义
--dirstat
的行为。默认值由diff.dirstat
配置变量控制(参见 git-config[1])。以下参数可用:changes
-
通过计算从源文件删除或添加到目标文件的行数来计算目录统计数字。这忽略了文件中纯代码移动的数量。换句话说,重新排列文件中的行与其它更改的计数不同。这是未给出参数时的默认行为。
lines
-
通过执行常规的基于行的差异分析并汇总删除/添加的行数来计算 dirstat 数字。(对于二进制文件,则计算 64 字节块,因为二进制文件没有自然的行概念)。这比
changes
行为是一种更昂贵的--dirstat
行为,但它会将文件中重新排列的行与其他更改一样计算在内。结果输出与您从其他--*stat
选项获得的输出一致。 files
-
通过计算更改的文件数来计算 dirstat 数字。每个更改的文件在 dirstat 分析中权重相等。这是计算成本最低的
--dirstat
行为,因为它根本不需要查看文件内容。 cumulative
-
同时计算子目录中对父目录的更改。请注意,当使用
cumulative
时,报告的百分比总和可能超过 100%。默认(非累积)行为可以通过noncumulative
参数指定。 - <limit>
-
一个整数参数,指定一个截止百分比(默认为 3%)。对更改贡献低于此百分比的目录不会显示在输出中。
示例:以下将计算更改的文件,同时忽略更改文件总数少于 10% 的目录,并将子目录计数累积到父目录中:
--dirstat=files,10,cumulative
。 --cumulative
-
--dirstat=cumulative
的同义词。 --dirstat-by-file
[=
<param>,...
]-
--dirstat=files,
<param>,...
的同义词。 --summary
-
输出扩展头信息的精简摘要,例如创建、重命名和模式更改。
--patch-with-stat
-
-p
--stat
的同义词。 -z
-
用 *NUL* 分隔提交,而不是用换行符。
此外,当给出
--raw
或--numstat
时,不要更改路径名,并使用 *NUL* 作为输出字段终止符。如果没有此选项,包含“不寻常”字符的路径名将按照配置变量
core.quotePath
的解释进行引用(参见 git-config[1])。 --name-only
-
仅显示后像树中每个已更改文件的名称。文件名通常以 UTF-8 编码。有关更多信息,请参阅 git-log[1] 手册页中关于编码的讨论。
--name-status
-
仅显示每个更改文件的名称和状态。有关状态字母的含义,请参见
--diff-filter
选项的描述。与--name-only
类似,文件名通常以 UTF-8 编码。 --submodule
[=
<format>]-
指定如何显示子模块中的差异。当指定
--submodule=short
时,使用short
格式。此格式仅显示范围开始和结束时的提交名称。当指定--submodule
或--submodule=log
时,使用log
格式。此格式像 git-submodule[1]summary
那样列出范围内的提交。当指定--submodule=diff
时,使用diff
格式。此格式以内联差异显示提交范围之间子模块内容的更改。默认为diff.submodule
,如果未设置配置选项,则默认为short
格式。 --color
[=
<when>]-
显示彩色差异。
--color
(即不带=
<when>)与--color=always
相同。<when> 可以是always
、never
或auto
之一。 --no-color
-
关闭彩色 diff。它与
--color=never
相同。 --color-moved
[=
<mode>]-
移动的代码行会以不同颜色显示。如果未给出此选项,则 *<mode>* 默认为
no
;如果给出此选项但未指定模式,则默认为zebra
。模式必须是以下之一:no
-
移动的行不进行高亮显示。
default
-
是
zebra
的同义词。未来可能会更改为更合理的模式。 plain
-
在某个位置添加但在另一个位置删除的任何行将以
color.diff.newMoved
颜色着色。类似地,color.diff.oldMoved
将用于在差异中其他地方添加的已删除行。此模式会检测任何移动的行,但在审查时,要确定代码块是否在没有置换的情况下移动,它并不是很有用。 blocks
-
贪婪地检测至少 20 个字母数字字符的移动文本块。检测到的块使用
color.diff.
(old
|new
)Moved
颜色绘制。相邻块无法区分。 zebra
-
移动的文本块的检测方式与
blocks
模式相同。这些块使用color.diff.
(old
|new
)Moved
颜色或color.diff.
(old
|new
)MovedAlternative
进行着色。两种颜色之间的变化表示检测到一个新块。 dimmed-zebra
-
与
zebra
类似,但会对移动代码中不重要的部分进行额外的弱化处理。两个相邻块的边界行被认为是重要的,其余部分不重要。dimmed_zebra
是一个已弃用的同义词。
--no-color-moved
-
关闭移动检测。这可以用于覆盖配置设置。它与
--color-moved=no
相同。 --color-moved-ws=
<mode>,...
-
这配置了在执行
--color-moved
的移动检测时如何忽略空白。这些模式可以作为逗号分隔的列表给出: --no-color-moved-ws
-
执行移动检测时不忽略空白。这可以用于覆盖配置设置。它与
--color-moved-ws=no
相同。 --word-diff
[=
<mode>]-
默认情况下,单词由空白分隔;参见下面的
--word-diff-regex
。<mode> 默认为plain
,并且必须是以下之一:请注意,尽管第一个模式的名称如此,如果启用,所有模式都使用颜色高亮显示更改的部分。
--word-diff-regex=
<regex>-
使用 <regex> 来决定什么是单词,而不是将非空白字符的连续序列视为一个单词。除非已启用,否则这也隐含
--word-diff
。*<regex>* 的每个不重叠匹配都被视为一个单词。这些匹配之间的任何内容都被视为空白并被忽略(!)以查找差异。您可能希望在正则表达式后面附加 |[
^
[:space:
]] 以确保它匹配所有非空白字符。包含换行符的匹配会在换行符处被静默截断(!)例如,
--word-diff-regex=.
会将每个字符视为一个单词,并相应地逐字符显示差异。正则表达式也可以通过 diff 驱动程序或配置选项设置,参见 gitattributes[5] 或 git-config[1]。显式给定它会覆盖任何 diff 驱动程序或配置设置。Diff 驱动程序优先于配置设置。
--color-words
[=
<regex>]-
相当于
--word-diff=color
加上(如果指定了正则表达式)--word-diff-regex=
<regex>。 --no-renames
-
关闭重命名检测,即使配置文件默认开启。
--
[no-
]rename-empty
-
是否使用空 blob 作为重命名源。
--check
-
如果更改引入了冲突标记或空白错误,则发出警告。空白错误的定义由
core.whitespace
配置控制。默认情况下,尾随空白(包括仅包含空白的行)和行初始缩进中紧跟制表符的空格字符被视为空白错误。如果发现问题,则以非零状态退出。与--exit-code
不兼容。 --ws-error-highlight=
<kind>-
在差异的
context
、old
或new
行中突出显示空白错误。多个值用逗号分隔,none
重置以前的值,default
将列表重置为new
,all
是old,new,context
的简写。如果未给出此选项,并且未设置配置变量diff.wsErrorHighlight
,则仅突出显示new
行中的空白错误。空白错误以color.diff.whitespace
着色。 --full-index
-
在生成补丁格式输出时,不在“index”行上显示前几个字符,而是显示完整的原图像和后图像 blob 对象名称。
--binary
-
除了
--full-index
之外,还输出一个二进制 diff,该 diff 可以用git-apply
应用。隐含--patch
。 --abbrev
[=
<n>]-
在 diff-raw 格式输出和 diff-tree 头部行中,不显示完整的 40 字节十六进制对象名称,而是显示最短的、至少 *<n>* 位十六进制长度的唯一引用该对象的前缀。在 diff-patch 输出格式中,
--full-index
具有更高优先级,即如果指定了--full-index
,无论是否指定--abbrev
,都将显示完整的 blob 名称。可以使用--abbrev=
<n> 指定非默认位数。 -B
[<n>][/
<m>]--break-rewrites
[=
[<n>][/
<m>]]-
将完整的重写更改分解为删除和创建对。这有两个目的:
它影响文件完全重写的更改的显示方式,不是作为一系列删除和插入与极少量文本匹配的上下文混合在一起,而是作为对所有旧内容的单个删除,然后对所有新内容的单个插入,数字 *<m>* 控制
-B
选项的这一方面(默认为 60%)。-B/70%
指定原始内容少于 30% 应保留在结果中,Git 才将其视为完全重写(即,否则生成的补丁将是一系列删除和插入与上下文行混合在一起)。当与
-M
一起使用时,一个完全重写的文件也被视为重命名的源(通常-M
只将消失的文件视为重命名的源),数字 *<n>* 控制-B
选项的这一方面(默认为 50%)。-B20%
指定与文件大小的 20% 或更多相比,有添加和删除的更改符合被视为可能重命名到另一个文件的源。 -M
[<n>]--find-renames
[=
<n>]-
如果生成差异,则检测并报告每个提交的重命名。对于在遍历历史记录时跨重命名跟踪文件,请参阅
--follow
。如果指定了<n>,则它是相似度指数的阈值(即与文件大小相比的添加/删除量)。例如,-M90%
表示如果文件有90%以上未更改,Git应将删除/添加对视为重命名。如果没有%
符号,则该数字被读取为小数,小数点位于数字之前。即,-M5
变为0.5,因此与-M50%
相同。类似地,-M05
与-M5%
相同。要将检测限制为精确重命名,请使用-M100%
。默认相似度指数为50%。 -C
[<n>]--find-copies
[=
<n>]-
检测复制和重命名。另请参见
--find-copies-harder
。如果指定了 <n>,其含义与-M
<n> 相同。 --find-copies-harder
-
出于性能原因,默认情况下,
-C
选项仅在副本的原始文件在同一变更集中被修改时才查找副本。此标志使命令检查未修改的文件作为副本源的候选。对于大型项目而言,这是一项非常耗费性能的操作,因此请谨慎使用。给定多个-C
选项具有相同的效果。 -D
--irreversible-delete
-
省略删除操作的原始图像,即仅打印头部,而不打印原始图像与
/dev/null
之间的差异。生成的补丁不适合通过patch
或git
apply
应用;这仅仅适用于希望专注于审查变更后文本的人。此外,输出显然缺乏足够的信息来反向应用此类补丁,即使是手动操作也如此,因此得名此选项。与
-B
一起使用时,也会省略删除/创建对的删除部分中的原始图像。 -l
<num>-
-M
和-C
选项涉及一些初步步骤,可以廉价地检测重命名/复制的子集,然后是一个详尽的回退部分,将所有剩余的未配对目标与所有相关源进行比较。(对于重命名,只有剩余的未配对源是相关的;对于复制,所有原始源都是相关的。)对于N个源和目标,这种详尽的检查是O(N^2)。如果涉及的源/目标文件数量超过指定数量,此选项将阻止重命名/复制检测的详尽部分运行。默认为diff.renameLimit
。请注意,值0被视为无限制。 --diff-filter=
[(A
|C
|D
|M
|R
|T
|U
|X
|B
)...
[*
]]-
仅选择已添加(
A
)、已复制(C
)、已删除(D
)、已修改(M
)、已重命名(R
)、类型(即普通文件、符号链接、子模块等)已更改(T
)、未合并(U
)、未知(X
)或配对已损坏(B
)的文件。可以使用过滤字符的任意组合(包括不使用)。当*
(全部或无)添加到组合中时,如果在比较中有任何文件匹配其他条件,则选择所有路径;如果没有文件匹配其他条件,则不选择任何内容。此外,这些大写字母可以小写以进行排除。例如,
--diff-filter=ad
会排除已添加和已删除的路径。请注意,并非所有 diff 都能包含所有类型。例如,如果禁用对这些类型的检测,则不会出现已复制和已重命名条目。
-S
<string>-
查找更改文件中指定 <string> 出现次数(即添加/删除)的差异。供脚本编写者使用。
当您正在寻找一个精确的代码块(如一个结构体),并想知道该代码块从首次出现以来的历史记录时,这很有用:迭代使用此功能,将原始图像中有趣的代码块重新输入到
-S
中,并持续操作直到获得该代码块的第一个版本。二进制文件也会被搜索。
-G
<regex>-
查找其补丁文本包含与 <regex> 匹配的添加/删除行的差异。
为了说明
-S
<regex>--pickaxe-regex
和-G
<regex>之间的区别,请考虑一个在同一文件中具有以下差异的提交:+ return frotz(nitfol, two->ptr, 1, 0); ... - hit = frotz(nitfol, mf2.ptr, 1, 0);
虽然git log -G"frotz\(nitfol"将显示此提交,但git log -S"frotz\(nitfol" --pickaxe-regex不会显示(因为该字符串的出现次数没有改变)。
除非提供了
--text
,否则没有 textconv 过滤器的二进制文件的补丁将被忽略。有关更多信息,请参见 gitdiffcore[7] 中的 *pickaxe* 条目。
--find-object=
<object-id>-
查找更改指定对象出现次数的差异。类似于
-S
,只是参数不同,它不搜索特定字符串,而是搜索特定对象 ID。该对象可以是 blob 或子模块提交。它隐含了
git-log
中的-t
选项,以也查找树。 --pickaxe-all
-
当
-S
或-G
找到更改时,显示该变更集中所有更改,而不仅仅是包含 <string> 更改的文件。 --pickaxe-regex
-
将提供给
-S
的 <string> 视为扩展的 POSIX 正则表达式进行匹配。 -O
<orderfile>-
控制文件在输出中出现的顺序。这会覆盖
diff.orderFile
配置变量(请参阅git-config[1])。要取消diff.orderFile
,请使用-O/dev/null
。输出顺序由<orderfile>中glob模式的顺序决定。所有路径名匹配第一个模式的文件首先输出,所有路径名匹配第二个模式(但不匹配第一个)的文件其次输出,依此类推。所有路径名不匹配任何模式的文件最后输出,就像文件末尾有一个隐式的全匹配模式一样。如果多个路径名具有相同的优先级(它们匹配相同的模式但没有更早的模式),则它们相对于彼此的输出顺序是正常的顺序。
<orderfile> 解析如下:
-
空行被忽略,因此它们可以用作分隔符以提高可读性。
-
以井号("
#
")开头的行被忽略,因此它们可以用作注释。如果模式以井号开头,请在模式开头添加反斜杠("\")。 -
其他每行包含一个模式。
模式具有与
fnmatch
(3)不带FNM_PATHNAME
标志时所用模式相同的语法和语义,但如果删除任意数量的最终路径名组件后匹配该模式,则路径名也匹配该模式。例如,模式"foo*bar
"匹配"fooasdfbar
"和"foo/bar/baz/asdf
"但不匹配"foobarx
"。 -
--skip-to=
<file>--rotate-to=
<file>-
从输出中丢弃命名<file>之前的文件(即跳到),或将其移到输出的末尾(即旋转到)。这些选项主要为
git
difftool
命令的使用而发明,否则可能用处不大。 -R
-
交换两个输入;即,显示从索引或磁盘文件到树内容的差异。
--relative
[=
<path>]--no-relative
-
当从项目的子目录中运行时,可以使用此选项排除目录外的更改并显示相对于该目录的路径名。当您不在子目录中时(例如在裸仓库中),可以通过提供<path>作为参数来命名要使输出相对于哪个子目录。
--no-relative
可用于抵消diff.relative
配置选项和先前的--relative
。 -a
--text
-
将所有文件视为文本。
--ignore-cr-at-eol
-
进行比较时忽略行尾的回车符。
--ignore-space-at-eol
-
忽略行尾空格的更改。
-b
--ignore-space-change
-
忽略空格数量的变化。这会忽略行尾的空格,并将所有其他一个或多个空格序列视为等效。
-w
--ignore-all-space
-
比较行时忽略空格。即使一行有空格而另一行没有,这也忽略了差异。
--ignore-blank-lines
-
忽略所有空行的更改。
-I
<regex>--ignore-matching-lines=
<regex>-
忽略所有行都匹配 <regex> 的更改。此选项可以多次指定。
--inter-hunk-context=
<number>-
在差异块之间显示上下文,最多达指定行数 <number>,从而合并彼此接近的块。默认为
diff.interHunkContext
,如果未设置配置选项则为 0。 -W
--function-context
-
将整个函数作为每个变更的上下文行显示。函数名称的确定方式与
git
diff
计算补丁块头部的方式相同(参见gitattributes[5]中的“Defining a custom hunk-header”)。 --ext-diff
-
允许执行外部差异辅助程序。如果您使用 gitattributes[5] 设置了外部差异驱动程序,则需要与 git-log[1] 等命令一起使用此选项。
--no-ext-diff
-
禁止外部差异驱动程序。
--textconv
--no-textconv
-
允许(或禁止)在比较二进制文件时运行外部文本转换过滤器。详情请参阅gitattributes[5]。由于textconv过滤器通常是单向转换,因此生成的差异适合人类阅读,但无法应用。因此,textconv过滤器默认仅对git-diff[1]和git-log[1]启用,但不对git-format-patch[1]或diff底层命令启用。
--ignore-submodules
[=
(none
|untracked
|dirty
|all
)]-
在生成差异时忽略对子模块的更改。
all
是默认值。使用none
将在子模块包含未跟踪或已修改文件,或其HEAD
与超项目中记录的提交不同时,将其视为已修改,并且可以覆盖git-config[1]或gitmodules[5]中ignore
选项的任何设置。当使用untracked
时,如果子模块仅包含未跟踪内容,则不将其视为脏(但仍会扫描其修改内容)。使用dirty
会忽略子模块工作树的所有更改,仅显示超项目中存储的提交的更改(这是1.7.0之前的行为)。使用all
会隐藏所有对子模块的更改。 --src-prefix=
<prefix>-
显示给定的源前缀 <prefix> 而不是 "a/"。
--dst-prefix=
<prefix>-
显示给定的目标前缀 <prefix> 而不是 "b/"。
--no-prefix
-
不显示任何源或目标前缀。
--default-prefix
-
使用默认的源和目标前缀("a/" 和 "b/")。这会覆盖配置变量,例如
diff.noprefix
、diff.srcPrefix
、diff.dstPrefix
和diff.mnemonicPrefix
(请参阅git-config[1])。 --line-prefix=
<prefix>-
在每行输出前面添加一个额外的 <prefix>。
--ita-invisible-in-index
-
默认情况下,由
git
add
-N
添加的条目在git
diff
中显示为现有空文件,在git
diff
--cached
中显示为新文件。此选项使条目在git
diff
中显示为新文件,在git
diff
--cached
中显示为不存在。此选项可以使用--ita-visible-in-index
恢复。这两个选项都是实验性的,将来可能会被移除。
有关这些通用选项的更详细说明,另请参见 gitdiffcore[7]。
使用 -p 生成补丁文本
运行git-diff[1]、git-log[1]、git-show[1]、git-diff-index[1]、git-diff-tree[1]或git-diff-files[1]时带-p
选项会产生补丁文本。您可以通过GIT_EXTERNAL_DIFF
和GIT_DIFF_OPTS
环境变量(参见git[1]),以及diff
属性(参见gitattributes[5])自定义补丁文本的创建。
-p
选项生成的输出与传统的 diff 格式略有不同:
-
它前面是“git diff”头,看起来像这样:
diff --git a/file1 b/file2
除非涉及重命名/复制,否则
a/
和b/
文件名相同。特别是,即使是创建或删除,也不会使用/dev/null
来代替a/
或b/
文件名。当涉及重命名/复制时,
file1
和file2
分别显示重命名/复制的源文件名称和重命名/复制生成的文件名称。 -
后面跟着一个或多个扩展头行:
old
mode
<mode>new
mode
<mode>deleted
file
mode
<mode>new
file
mode
<mode>copy
from
<path>copy
to
<path>rename
from
<path>rename
to
<path>similarity
index
<number>dissimilarity
index
<number>index
<hash>..
<hash> <mode>文件模式 <mode> 以 6 位八进制数字打印,包括文件类型和文件权限位。
扩展头中的路径名不包含
a/
和b/
前缀。相似度指数是未更改行的百分比,而相异度指数是已更改行的百分比。它是一个向下取整的整数,后跟一个百分号。因此,100%的相似度指数值保留给两个完全相同的文件,而100%的相异度意味着旧文件中的任何行都没有进入新文件。
索引行包括更改前后的 blob 对象名称。如果文件模式没有更改,则包含 <mode>;否则,单独的行指示旧模式和新模式。
-
包含“不寻常”字符的路径名将按照配置变量
core.quotePath
的解释进行引用(参见 git-config[1])。 -
输出中所有
file1
文件都指提交前的文件,所有file2
文件都指提交后的文件。顺序地将每个更改应用于每个文件是不正确的。例如,此补丁将交换a和bdiff --git a/a b/b rename from a rename to b diff --git a/b b/a rename from b rename to a
-
Hunk 头会提及 hunk 应用到的函数名称。有关如何根据特定语言进行调整的详细信息,请参见 gitattributes[5] 中的“定义自定义 hunk-header”。
组合 diff 格式
任何生成差异的命令都可以带-c
或--cc
选项来在显示合并时生成合并差异。这是用git-diff[1]或git-show[1]显示合并时的默认格式。另请注意,您可以为这些命令中的任何一个提供合适的--diff-merges
选项,以强制生成特定格式的差异。
“组合 diff”格式如下所示:
diff --combined describe.c index fabadb8,cc95eb0..4866510 --- a/describe.c +++ b/describe.c @@@ -98,20 -98,12 +98,20 @@@ return (a_date > b_date) ? -1 : (a_date == b_date) ? 0 : 1; } - static void describe(char *arg) -static void describe(struct commit *cmit, int last_one) ++static void describe(char *arg, int last_one) { + unsigned char sha1[20]; + struct commit *cmit; struct commit_list *list; static int initialized = 0; struct commit_name *n; + if (get_sha1(arg, sha1) < 0) + usage(describe_usage); + cmit = lookup_commit_reference(sha1); + if (!cmit) + usage(describe_usage); + if (!initialized) { initialized = 1; for_each_ref(get_name);
-
它前面是“git diff”头,看起来像这样(使用
-c
选项时):diff --combined file
或者像这样(使用
--cc
选项时):diff --cc file
-
后面跟着一个或多个扩展头行(此示例显示了一个包含两个父级的合并):
index
<hash>,
<hash>..
<hash>mode
<mode>,
<mode>..
<mode>new
file
mode
<mode>deleted
file
mode
<mode>,
<mode>mode
<mode>,
<mode>..
<mode>行仅当至少一个<mode>与其他不同时出现。带有检测到的内容移动(重命名和复制检测)信息的扩展头部旨在用于两个<tree-ish>的差异,并且不用于合并差异格式。 -
后面跟着一个两行的“源文件/目标文件”头:
--- a/file +++ b/file
类似于传统 unified diff 格式的两行头,
/dev/null
用于指示已创建或已删除的文件。然而,如果提供了 --combined-all-paths 选项,您将得到一个 N+1 行的“源文件/目标文件”头,而不是两行的“源文件/目标文件”头,其中 N 是合并提交中父级的数量:
--- a/file --- a/file --- a/file +++ b/file
如果重命名或复制检测处于活动状态,这种扩展格式会很有用,可以让您查看不同父级中文件的原始名称。
-
块头部格式已修改,以防止人们意外地将其馈送给
patch
-p1
。合并差异格式是为了审查合并提交更改而创建的,并非用于应用。该更改类似于扩展索引头部中的更改@@@ <from-file-range> <from-file-range> <to-file-range> @@@
组合 diff 格式的块头中有(父级数量 + 1)个
@
字符。
与传统的统一差异格式不同,后者显示两个文件A和B,带有一个单列,其中包含-
(减号——出现在A中但在B中被移除)、+
(加号——在A中缺失但在B中添加)或"
"
(空格——未更改)前缀,此格式比较两个或更多文件file1、file2等与一个文件X,并显示X与每个fileN的不同之处。每行输出前面都会加上一个对应每个fileN的列,以注明X的行与它的不同。
列N中的-
字符表示该行出现在fileN中,但未出现在结果中。列N中的+
字符表示该行出现在结果中,而fileN没有该行(换句话说,从该父级的角度来看,该行是新增的)。
在上述示例输出中,函数签名从两个文件(因此从file1和file2中删除了两个-
,加上++
表示添加的一行既未出现在file1中也未出现在file2中)都被更改了。此外,其他八行与file1相同但未出现在file2中(因此带有+
前缀)。
当通过git
diff-tree
-c
显示时,它会比较合并提交的父级与合并结果(即file1..fileN是父级)。当通过git
diff-files
-c
显示时,它会比较两个未解决的合并父级与工作树文件(即file1是阶段2,也称为“我们的版本”,file2是阶段3,也称为“他们的版本”)。
讨论
Git 在某种程度上是字符编码无关的。
-
blob 对象的内容是未经解释的字节序列。核心层面没有编码转换。
-
路径名以UTF-8规范化形式C编码。这适用于树对象、索引文件、引用名称以及命令行参数、环境变量和配置文件(
.git/config
(参见git-config[1])、gitignore[5]、gitattributes[5]和gitmodules[5])中的路径名。请注意,Git在核心层面将路径名简单地视为非NUL字节序列,没有路径名编码转换(Mac和Windows除外)。因此,即使在使用传统扩展ASCII编码的平台和文件系统上,使用非ASCII路径名也大多能正常工作。然而,在此类系统上创建的仓库在基于UTF-8的系统(例如Linux、Mac、Windows)上将无法正常工作,反之亦然。此外,许多基于Git的工具简单地假定路径名为UTF-8,并且将无法正确显示其他编码。
-
提交日志消息通常以UTF-8编码,但也支持其他扩展ASCII编码。这包括ISO-8859-x、CP125x和许多其他编码,但不包括UTF-16/32、EBCDIC和CJK多字节编码(GBK、Shift-JIS、Big5、EUC-x、CP9xx等)。
尽管我们鼓励提交日志消息使用UTF-8编码,但核心和Git Porcelain的设计并不会强制项目使用UTF-8。如果特定项目的所有参与者都认为使用传统编码更方便,Git并不会禁止。但是,有几点需要记住。
-
git
commit
和git
commit-tree
在给定提交日志消息看起来不像有效的UTF-8字符串时会发出警告,除非您明确说明您的项目使用传统编码。声明此信息的方式是在.git/config
文件中设置i18n.commitEncoding
,例如:[i18n] commitEncoding = ISO-8859-1
使用上述设置创建的提交对象会在其
encoding
头部中记录i18n.commitEncoding
的值。这是为了帮助以后查看它们的人。缺少此头部意味着提交日志消息以UTF-8编码。 -
git
log
、git
show
、git
blame
及其相关命令会查看提交对象的encoding
头部,并尝试将日志消息重新编码为UTF-8,除非另有指定。您可以通过在.git/config
文件中设置i18n.logOutputEncoding
来指定所需的输出编码,例如:[i18n] logOutputEncoding = ISO-8859-1
如果您没有此配置变量,则会使用
i18n.commitEncoding
的值。
请注意,我们故意选择在提交时不对提交日志消息进行重新编码以强制在提交对象级别使用 UTF-8,因为重新编码为 UTF-8 不一定是可逆操作。