В репозитории git есть ли разница/польза с помощью git grep
по добрым старым grep
?
Примером может быть?
Лучше ли использовать git grep, чем обычный grep, если мы хотим искать в версированном исходном коде?
Ответ 1
Оба очень похожи. Основное отличие заключается в том, что git grep
по умолчанию выполняет поиск в файлах, которые отслеживаются с помощью git.
Примеры
Если я хочу найти foo
в моем проекте, я могу использовать git grep
или хороший ol 'автономный grep
:
git grep foo
grep -R foo .
Версия git grep
будет выполнять поиск только в файлах, отслеживаемых git, тогда как версия grep
будет искать все в каталоге. До сих пор такой схожий; любой из них может быть лучше в зависимости от того, чего вы хотите достичь.
Что делать, если мы хотим ограничить поиск только .rb
файлами?
git grep foo -- *.rb
grep -R --include=*.rb foo .
Простая старая версия grep
становится немного более многословной, но если вы привыкли использовать grep
, это может быть не проблема. Они по-прежнему не будут искать точно такие же файлы, но опять же это зависит от того, чего вы хотите достичь.
Как насчет поиска в предыдущей версии проекта?
git grep foo HEAD^
git checkout HEAD^; grep -R foo .; git checkout -
Здесь git grep
имеет реальную разницу: вы можете искать в другой версии проекта, не проверяя его в первую очередь. Это не такая ситуация, которая возникает слишком часто для меня; Обычно я хочу искать в версии проекта, который я проверил.
Настройка git grep
Есть несколько переменных git config
, которые изменяют поведение git grep
и избегают необходимости передавать пару аргументов командной строки:
-
grep.lineNumber
: всегда указывайте номера строк совпадений (вы можете передать-n
наgrep
иgit grep
, чтобы получить это поведение) -
grep.extendedRegexp
: всегда используйте расширенные регулярные выражения (вы можете передать-E
какgrep
, так иgit grep
, чтобы получить это поведение)
На практике
На практике у меня gg
с псевдонимом git grep -En
, и это почти всегда делает то, что я хочу.
Ответ 2
Основным преимуществом git grep
является то, что он может найти шаблоны в репозитории git, т.е. е. также в других версиях, чем текущая версия источника. Конечно, это невозможно сделать с помощью стандартного grep
. Кроме того, в арифметике git grep
аналогично шаблону (например, git grep -e pattern1 --and --not \( -e pattern2 -e pattern3 \)
) есть намного больше возможностей, поиск по дереву с использованием glob (например, git grep pattern -- '*.[ch]'
для поиска только в файлах .c
и .h
) и еще несколько.
Здесь пример сеанса для поиска в старой версии:
$ mkdir git-test # create fresh repository
$ cd git-test/
$ git init .
Initialized empty Git repository in /home/alfe/git-test/.git/
$ echo eins zwei drei > bla # create example file
$ git add bla # add and commit it
$ git commit bla
[master (root-commit) 7494515] .
1 file changed, 1 insertion(+)
create mode 100644 bla
$ echo vier fuenf sechs > bla # perform a change on that file
$ git commit -m 'increase' bla # commit it
[master 062488e] increase
1 file changed, 1 insertion(+), 1 deletion(-)
$ git grep eins | cat # grep for outdated pattern in current version
# (finds nothing)
$ git grep eins master^ | cat # grep for outdated pattern on former version
# finds it:
master^:bla:eins zwei drei
Ответ 3
Если вы ищете шаблоны/строки в репозитории git (т.е. в файлах, которые уже отслеживаются), тогда да, git grep должен быть намного быстрее, чем обычный grep, поскольку он индексируется. (Вы можете попробовать это вручную, git -grep должен быть заметно быстрее)
Ответ 4
git grep
выполняет поиск только в отслеживаемых файлах в репо.
С помощью grep
вам нужно передать список файлов для поиска, и вы сами отфильтровывали бы любые невоспроизводимые файлы.
Итак, если вы ищете что-то, что знаете в репо, git grep
экономит ваше время, так как все, что вам нужно сделать, это предоставить шаблон. Это также полезно, если вам не нужно искать все, что не отслеживается в репо.