Не могли бы вы изменить свой принятый ответ? Большинству нравится --is-ancestorрешение.
Роберт Симер
Ответы:
51
Если вы хотите проверить это программно (например, в скрипте), вы можете проверить, git merge-base A Bравно ли оно git rev-parse --verify A(тогда A достижимо из B), или если это так git rev-parse --verify B(тогда B достижимо из A). git rev-parseЗдесь необходимо преобразовать имя коммита в коммит SHA-1 / commit id.
Использование ответаgit rev-list как в VonC также возможно.
Изменить: в современном Git есть явная поддержка этого запроса в виде git merge-base --is-ancestor.
Если один из коммитов, о котором вы спрашиваете, является подсказкой ветки , тогда git branch --contains <commit>или git branch --merged <commit>может быть лучшим непрограммным решением.
Возможно, самый быстрый способ был бы git checkout -b quickcheck <more-recent-commit-ID>тогда и тогда git branch --contains <older-commit-ID>(а затем git branch -D quickcheckизбавиться от временной ветки).
Кли
2
Два возможных подхода, оба намного хуже, чем в ответе @ MattR.
JWG
6
@jwg: Ответ MattR лучше, но этот ответ (и, вероятно, его принимают) предшествует git 1.8.0 и git merge-base --is-ancestor2 годам.
Якуб Наренбский
@ JakubNarębski Достаточно справедливо, извините.
JWG
2
В большом репозитории (2 миллиона коммитов) я сравнил скорость git branch --contains <commit>и git merge-base --is-ancestor ...: 3m40s против 0,14s
hagello
259
В Git 1.8.0 это поддерживается как опция для merge-base:
Проверьте, является ли первый предком второго, и выйдите со статусом 0, если истина, или со статусом 1, если нет. Ошибки сигнализируются ненулевым статусом, отличным от 1.
@smarber git merge-base --is-ancestor -- commit commitработает для хэшей на моей стороне с git2.1.4 (Debian / Devuan 7.10 jessie) и 1.9.1 (Ubuntu 14.04 trusty), которые сейчас довольно древние. Это работает даже для Debian Wheezy, если вы делаете sudo apt-get install git/wheezy-backports.
Если последний отображаемый коммит совпадает с первым коммитом в git rev-listкоманде, то это коммит, достижимый из второго коммита.
Если первый коммит недоступен со второго, git rev-listничего не должно возвращаться.
git rev-list --boundary A..B
закончил бы A, если Aдостижим от B.
Это так же, как:
git rev-list --boundary B --not A
с Bболее положительной ссылкой , и Aв отрицательном значении задания .
Он начинается с Bи идет назад по графику, пока не встретит ревизию, из которой можно добраться A.
Я бы сказал, что если к нему Aможно напрямую добраться B, он сам столкнется (и покажет, из-за --boundaryопции) A.
Это звучит как достаточно распространенный сценарий использования, и я удивлен, что git еще не опубликовал «фарфоровую» команду, которая делает именно это.
О, чувак, похоже, мне нужно вернуться и поработать над сценариями в Shell!
Лоуренс И. Сиден
1
вопрос: почему -85e54e2...во фрагменте есть минус? Также возможна опечатка: "... это то же самое, что первый коммит ..."
sdaau
1
@sdaau -означает, что это граничный коммит. Я отредактировал ответ, чтобы сделать его более понятным, а также обновить ссылки на документы и исправить опечатку для этого 5-летнего ответа.
VonC
11
Другим способом было бы использовать git logи grep.
git log --pretty=format:%H abc123 | grep def456
Это выдаст одну строку вывода, если commit def456 является предком коммита abc123, или не выводит иначе.
Обычно вы можете обойтись без пропуска --prettyаргумента, но это необходимо, если вы хотите убедиться, что вы осуществляете поиск только по реальным хэшам коммитов, а не по комментариям журналов и так далее.
Структура commit используется во многих контекстах. Однако члены generationи graph_posиспользуются только для операций, связанных с графом фиксации, и в противном случае тратят память.
Эта потеря была бы более заметной, когда мы перейдем к поколению номер v2, которое использует 64-разрядный номер поколения вместо текущих 32-разрядных.
Поскольку к ним часто обращаются вместе, давайте представим struct commit_graph_dataи переместим их в commit_graph_dataslab.
Хотя весь набор тестов работает так же быстро, как master(серии: 26 м48 с master: 27 м34 с, более быстрым на 2,87%), некоторые команды вроде git merge-base --is-ancestorбыли замедлены на 40%, как обнаружил Седер Габор .
После минимизации доступа на уровне коммитов замедление сохраняется, но оно приближается к 20%.
Деррик Столи считает, что замедление связано с базовым алгоритмом, а не с медленным доступом к коммит-блокам, и мы продолжим это в следующих статьях .
--is-ancestor
решение.Ответы:
Если вы хотите проверить это программно (например, в скрипте), вы можете проверить,
git merge-base A B
равно ли оноgit rev-parse --verify A
(тогда A достижимо из B), или если это такgit rev-parse --verify B
(тогда B достижимо из A).git rev-parse
Здесь необходимо преобразовать имя коммита в коммит SHA-1 / commit id.Использование ответа
git rev-list
как в VonC также возможно.Изменить: в современном Git есть явная поддержка этого запроса в виде
git merge-base --is-ancestor
.Если один из коммитов, о котором вы спрашиваете, является подсказкой ветки , тогда
git branch --contains <commit>
илиgit branch --merged <commit>
может быть лучшим непрограммным решением.источник
git checkout -b quickcheck <more-recent-commit-ID>
тогда и тогдаgit branch --contains <older-commit-ID>
(а затемgit branch -D quickcheck
избавиться от временной ветки).git merge-base --is-ancestor
2 годам.git branch --contains <commit>
иgit merge-base --is-ancestor ...
: 3m40s против 0,14sВ Git 1.8.0 это поддерживается как опция для
merge-base
:Со страницы руководства:
Например:
источник
git merge-base THING --is-ancestor OF_THING && echo yes || echo no
например:git merge-base my-feature-branch --is-ancestor master && echo yes || echo no
git merge-base --is-ancestor -- commit commit
работает для хэшей на моей стороне сgit
2.1.4 (Debian / Devuan 7.10 jessie) и 1.9.1 (Ubuntu 14.04 trusty), которые сейчас довольно древние. Это работает даже для Debian Wheezy, если вы делаетеsudo apt-get install git/wheezy-backports
.Этот вид операций опирается на понятие диапазона ревизий, подробно описанное в вопросе SO: « Разница в 'git log origin / master' и 'git log origin / master ..' ".
git rev-list
должен быть в состоянии вернуться от коммита, до другого, если он достижим.Поэтому я бы попробовал:
(Граничные коммиты начинаются с префикса
-
)Если последний отображаемый коммит совпадает с первым коммитом в
git rev-list
команде, то это коммит, достижимый из второго коммита.Если первый коммит недоступен со второго,
git rev-list
ничего не должно возвращаться.закончил бы
A
, еслиA
достижим отB
.Это так же, как:
с
B
более положительной ссылкой , иA
в отрицательном значении задания .Он начинается с
B
и идет назад по графику, пока не встретит ревизию, из которой можно добратьсяA
.Я бы сказал, что если к нему
A
можно напрямую добратьсяB
, он сам столкнется (и покажет, из-за--boundary
опции)A
.источник
-85e54e2...
во фрагменте есть минус? Также возможна опечатка: "... это то же самое, что первый коммит ..."-
означает, что это граничный коммит. Я отредактировал ответ, чтобы сделать его более понятным, а также обновить ссылки на документы и исправить опечатку для этого 5-летнего ответа.Другим способом было бы использовать
git log
иgrep
.Это выдаст одну строку вывода, если commit def456 является предком коммита abc123, или не выводит иначе.
Обычно вы можете обойтись без пропуска
--pretty
аргумента, но это необходимо, если вы хотите убедиться, что вы осуществляете поиск только по реальным хэшам коммитов, а не по комментариям журналов и так далее.источник
--pretty
использовать --oneline:git log --oneline ce2ee3d | grep ec219cc
прекрасно работаетhttps://stackoverflow.com/a/13526591/895245 упоминает об этом, теперь, чтобы сделать его более дружелюбным к человеку:
источник
git show-branch branch-sha1 commit-sha1
Куда:
источник
Если вы используете
git merge-base --is-ancestor
, обязательно используйте Git 2.28 (3 квартал 2020 г.)В Git 2.28 (Q3 2020) несколько полей в «
struct commit
», которые не обязательно должны присутствовать, были перемещены для фиксации плит.См. Коммит c752ad0 , коммит c49c82a , коммит 4844812 , коммит 6da43d9 (17 июня 2020 г.) от Abhishek Kumar (
abhishekkumar2718
) .(Слиты Junio C Hamano -
gitster
- в фиксации d80bea4 , 6 июля 2020)источник
Основываясь на ответе itub, на случай, если вам нужно будет сделать это для всех тегов в хранилище:
источник