24

我希望git diff按文件名过滤结果。

特别是,我想要所有名为“AssemblyInfo.cs”但位于 git 存储库中任何位置的文件的差异。

我在 Cygwin 上使用 git,如果这有什么不同的话。

4

6 回答 6

26

最简单的方法是简单地使用通配符:

git diff -- '*AssemblyInfo.cs'


至少这适用于我的 Git v1.8.4、bash 3.2 和 zsh 5.7。

于 2015-08-28T00:31:11.783 回答
18

文件参数git diff需要被分隔--- 试试这个:

find . -name <pattern> | xargs git diff --

xargs 确保正确处理空格、制表符、换行符等。

您可以--name-status使用git diff. 你也可以试试:

git diff --name-only | grep <pattern>

[编辑] 尝试:

git diff --name-status -- `find . -name '<pattern>'`
ebg@taiyo(98)$ git diff --name-status -- `find . -name '*.scm'`
M       scheme/base/boolean.scm
M       surf/compiler/common.scm
M       surf/compiler/compile.scm
M       surf/compiler/expand.scm
于 2013-03-15T18:09:48.517 回答
5

可能最简单的选择是使用:

git diff "*/*AssemlyInfo.cs"

从 git 2.20.1 开始工作

于 2019-07-23T01:43:04.980 回答
0

While the answer given by GoZoner works for some (hundred?) files, it executes git diff multiple times (in the case of xargs) or fails (in the case of git diff … -- `find …`) if there is a large number of files to diff. This might be a problem or not, depending on your use case.

A possible solution is to create a commit containing only changes to files of interest and diff the commits. Based on an answer on unstaging files matching some pattern I came up with this solution:

git co <new_branch> --detach
git reset --soft <old_branch>

Now git status --porcelain | grep <pattern> shows all files that should be compared. All other files can be listed by passing -v to grep, i.e. git status --porcelain | grep -v <pattern>. This files need to be reset to the state of <old_branch>:

# Remove the destination of renamed and copied files not matching <pattern>
git status --porcelain | grep -v <pattern> | grep '^R \|^C ' | sed 's/.* -> //' | xargs git rm -f --
# Remove added files not matching <pattern>
git status --porcelain | grep -v <pattern> | grep '^A ' | cut -c 4- | xargs git rm -f --
# Restore deleted files not matching <pattern>
git status --porcelain | grep -v <pattern> | grep '^M \|^D ' | cut -c 4- | xargs git checkout HEAD --

(Note that using xargs is not a problem in this case, as calling git rm and git checkout multiple times is ok.)

Now the index (and working copy) only contains changes to the files matched by <pattern>. The next thing to do is to commit this changes:

git commit -m "Changes between <old_branch> and <new_branch> in files matching <pattern>"

That's it! Now we can use git diff as usual:

git diff HEAD^..HEAD

You can use all options or arguments you like.

Note: This solution is not tested extensively and may fail e.g. on files with special characters or other special cases… Suggestions to improve the solution are welcome ;-)

于 2014-12-06T23:15:28.310 回答
0

You can use pipeline

find . -name AssemblyInfo.cs | git diff

Use find to filter all the files named "AssemblyInfo.cs", then use the output as the parameter of git diff.

于 2013-03-15T17:49:53.613 回答
0
find . -iregex AssemblyInfo\.cs -exec git diff {} +

你可以AssemblyInfo\.cs用你的正则表达式替换。

于 2016-11-23T13:04:31.477 回答