使用git diff,我怎样才能得到添加和修改的行号?

假设我有一个文本文件

alex bob matrix will be removed git repo 

我已经更新了

 alex new line here another new line bob matrix git 

在这里,我添加了行号(2,3)和行号(6)

如何使用git diff或其他任何git命令获取这些行号信息?

git diff --stat会显示你提交的东西,这是你所指的那个东西,我猜。

 git diff --stat 

要准确显示已经更改的行号,您可以使用

 git blame -p <file> | grep "Not Committed Yet" 

并且结果中改变的行将是结束括号之前的最后一个数字。 不是一个干净的解决scheme

这是一个bash函数,用于计算差异结果行数:

 diff-lines() { local path= local line= while read; do esc=$'\033' if [[ $REPLY =~ ---\ (a/)?.* ]]; then continue elif [[ $REPLY =~ \+\+\+\ (b/)?([^[:blank:]$esc]+).* ]]; then path=${BASH_REMATCH[2]} elif [[ $REPLY =~ @@\ -[0-9]+(,[0-9]+)?\ \+([0-9]+)(,[0-9]+)?\ @@.* ]]; then line=${BASH_REMATCH[2]} elif [[ $REPLY =~ ^($esc\[[0-9;]+m)*([\ +-]) ]]; then echo "$path:$line:$REPLY" if [[ ${BASH_REMATCH[2]} != - ]]; then ((line++)) fi fi done } 

它可以产生如下的输出:

 $ git diff | diff-lines http-fetch.c:1: #include "cache.h" http-fetch.c:2: #include "walker.h" http-fetch.c:3: http-fetch.c:4:-int cmd_http_fetch(int argc, const char **argv, const char *prefix) http-fetch.c:4:+int main(int argc, const char **argv) http-fetch.c:5: { http-fetch.c:6:+ const char *prefix; http-fetch.c:7: struct walker *walker; http-fetch.c:8: int commits_on_stdin = 0; http-fetch.c:9: int commits; http-fetch.c:19: int get_verbosely = 0; http-fetch.c:20: int get_recover = 0; http-fetch.c:21: http-fetch.c:22:+ prefix = setup_git_directory(); http-fetch.c:23:+ http-fetch.c:24: git_config(git_default_config, NULL); http-fetch.c:25: http-fetch.c:26: while (arg < argc && argv[arg][0] == '-') { fetch.h:1: #include "config.h" fetch.h:2: #include "http.h" fetch.h:3: fetch.h:4:-int cmd_http_fetch(int argc, const char **argv, const char *prefix); fetch.h:4:+int main(int argc, const char **argv); fetch.h:5: fetch.h:6: void start_fetch(const char* uri); fetch.h:7: bool fetch_succeeded(int status_code); 

从这样的差异:

 $ git diff diff --git a/builtin-http-fetch.cb/http-fetch.c similarity index 95% rename from builtin-http-fetch.c rename to http-fetch.c index f3e63d7..e8f44ba 100644 --- a/builtin-http-fetch.c +++ b/http-fetch.c @@ -1,8 +1,9 @@ #include "cache.h" #include "walker.h" -int cmd_http_fetch(int argc, const char **argv, const char *prefix) +int main(int argc, const char **argv) { + const char *prefix; struct walker *walker; int commits_on_stdin = 0; int commits; @@ -18,6 +19,8 @@ int cmd_http_fetch(int argc, const char **argv, const char *prefix) int get_verbosely = 0; int get_recover = 0; + prefix = setup_git_directory(); + git_config(git_default_config, NULL); while (arg < argc && argv[arg][0] == '-') { diff --git a/fetch.hb/fetch.h index 5fd3e65..d43e0ca 100644 --- a/fetch.h +++ b/fetch.h @@ -1,7 +1,7 @@ #include "config.h" #include "http.h" -int cmd_http_fetch(int argc, const char **argv, const char *prefix); +int main(int argc, const char **argv); void start_fetch(const char* uri); bool fetch_succeeded(int status_code); 

如果你只想显示添加/删除/修改的行,而不是周围的上下文,你可以传递-U0到git diff:

 $ git diff -U0 | diff-lines http-fetch.c:4:-int cmd_http_fetch(int argc, const char **argv, const char *prefix) http-fetch.c:4:+int main(int argc, const char **argv) http-fetch.c:6:+ const char *prefix; http-fetch.c:22:+ prefix = setup_git_directory(); http-fetch.c:23:+ fetch.h:4:-int cmd_http_fetch(int argc, const char **argv, const char *prefix); fetch.h:4:+int main(int argc, const char **argv); 

它对ANSI颜色代码是强大的,所以你可以通过--color=always来通过git diff来获得添加/去除行的通常的颜色编码。

输出可以很容易地被清除:

 $ git diff -U0 | diff-lines | grep 'main' http-fetch.c:4:+int main(int argc, const char **argv) fetch.h:4:+int main(int argc, const char **argv); 

在你的情况下, git diff -U0会给:

 $ git diff -U0 | diff-lines test.txt:2:+new line here test.txt:3:+another new line test.txt:6:-will be removed test.txt:6:-git repo test.txt:6:+git 

如果你只是想要行号,改变echo "$path:$line:$REPLY"只是echo "$line"和pipe道通过uniq输出。

我使用git diff--unified=0选项。

例如, git diff --unified=0 commit1 commit2输出diff:

*在这里输入图像说明*

由于--unified=0选项,diff输出显示0个上下文行; 换句话说,它显示了完全改变的线条

现在,您可以识别以“@@”开头的行,并根据模式进行parsing:

@@ -startline1,count1 +startline2,count2 @@

回到上面的例子,对于文件WildcardBinding.java,从第910行开始,删除了0行。 从第911行开始,添加4行。

我有这个相同的问题,所以我写了一个gawk脚本,它改变了git diff的输出,为每一行添加行号。 当我需要区分工作树时,我发现它有时很有用,但不限于此。 也许这里有人有用吗?

 $ git diff HEAD~1 |showlinenum.awk diff --git a/doc.txt b/doc.txt index fae6176..6ca8c26 100644 --- a/doc.txt +++ b/doc.txt @@ -1,3 +1,3 @@ 1: red 2: blue :-green 3:+yellow 

你可以在这里下载:
https://github.com/jay/showlinenum

所有未提交的行的行号(添加/修改):

 git blame <file> | grep -n '^0\{8\} ' | cut -f1 -d: 

示例输出:

 1 2 8 12 13 14 

configuration一个外部差异工具,它将显示行号。 例如,这是我在我的git全局configuration:

 diff.guitool=kdiff3 difftool.kdiff3.path=c:/Program Files (x86)/KDiff3/kdiff3.exe difftool.kdiff3.cmd="c:/Program Files (x86)/KDiff3/kdiff3.exe" "$LOCAL" "$REMOTE" 

请参阅此答案以获取更多详细信息: https : //stackoverflow.com/q/949242/526535

这是我拼凑在一起的一个bash函数:

 echo ${f}: for n in $(git --no-pager blame --line-porcelain $1 | awk '/author Not Committed Yet/{if (a && a !~ /author Not Committed Yet/) print a} {a=$0}' | awk '{print $3}') ; do if (( prev_line > -1 )) ; then if (( "$n" > (prev_line + 1) )) ; then if (( (prev_line - range_start) > 1 )) ; then echo -n "$range_start-$prev_line," else echo -n "$range_start,$prev_line," fi range_start=$n fi else range_start=$n fi prev_line=$n done if (( "$range_start" != "$prev_line" )) ; then echo "$range_start-$prev_line" else echo "$range_start" fi 

最后看起来像这样:

 views.py: 403,404,533-538,546-548,550-552,554-559,565-567,580-582 

不完全是你要求的,但git blame TEXTFILE可能会帮助。

你可以使用git diff加上shortstat参数来显示改变行号。

对于自上次提交以来更改的行数(在已经存在于回购中的文件中)

 git diff HEAD --shortstat 

它会输出类似的东西

 1 file changed, 4 insertions(+) 

这可能是相当准确的更改行数:

 git diff --word-diff <commit> |egrep '(?:\[-)|(?:\{\+)' |wc -l 

另外,这里是你的diff的行号解决scheme: https : //github.com/jay/showlinenum