Quelles sont les différences entre le double point «..» et le triple point «…» dans les plages de validation Git diff?

190

Quelles sont les différences entre les commandes suivantes?:

git diff foo master   # a 
git diff foo..master  # b
git diff foo...master # c

Le manuel diff en parle:

Comparer les branches

$ git diff topic master    <1>
$ git diff topic..master   <2>
$ git diff topic...master  <3>
  1. Changements entre les astuces du sujet et les branches principales.
  2. Comme ci-dessus.
  3. Modifications survenues sur la branche principale depuis le démarrage de la branche thématique.

mais n'est pas totalement clair pour moi.

chrisjlee
la source
Bien que la question ne soit pas un doublon, cette réponse montre graphiquement la signification de ..et ...dans git diffet leurs différentes significations dans git log.
Mark Longair

Réponses:

335

Puisque j'avais déjà créé ces images, j'ai pensé qu'il pourrait être utile de les utiliser dans une autre réponse, bien que la description de la différence entre ..(point-point) et ...(point-point-point) soit essentiellement la même que dans la réponse de manojlds .

La commande git diffne vous montre généralement que la différence entre les états de l'arborescence entre exactement deux points dans le graphe de validation. Les notations ..et ...dans git diffont les significations suivantes:

Une illustration des différentes manières de spécifier des commits pour git diff

En d'autres termes, git diff foo..barest exactement le même que git diff foo bar; les deux vous montreront la différence entre les pointes des deux branches fooet bar. D'autre part, git diff foo...barvous montrera la différence entre la "base de fusion" des deux branches et la pointe de bar. La "base de fusion" est généralement le dernier commit en commun entre ces deux branches, donc cette commande vous montrera les changements que votre travail bara introduits, tout en ignorant tout ce qui a été fait fooentre-temps.

C'est tout ce que vous devez savoir sur les notations ..et ...dans git diff. Toutefois...


... une source courante de confusion ici est cela ..et ...signifie des choses subtilement différentes lorsqu'elles sont utilisées dans une commande comme celle git logqui attend un ensemble de validations comme un ou plusieurs arguments. (Ces commandes finissent toutes par être utilisées git rev-listpour analyser une liste de commits à partir de leurs arguments.)

La signification de ..et ...pour git logpeut être représentée graphiquement comme ci-dessous:

Une illustration des différentes façons de spécifier des plages de commits pour git log

Donc, git rev-list foo..barvous montre tout sur la branche barqui n'est pas également sur la branche foo. D'autre part, git rev-list foo...barvous montre tous les commits qui sont dans l'un foo ou l' autre bar, mais pas les deux . Le troisième diagramme montre simplement que si vous listez les deux branches, vous obtenez les validations qui se trouvent dans l'une ou les deux.

Eh bien, je trouve que tout est un peu déroutant, de toute façon, et je pense que les diagrammes de graphe de validation aident :)

¹ Je dis seulement "typiquement" car lors de la résolution des conflits de fusion, par exemple, git diffvous montrera une fusion à trois.

Mark Longair
la source
1
J'aime tes schémas. J'ai aussi inventé le mien il y a quelque temps . J'ai quelques idées pour mes propres git diffdiagrammes que je ferai plus tard.
34
Quelqu'un a-t-il remarqué? Les effets de ..et se ...sentent renversées dans git diff( par rapport à git rev-list)!
Robert Siemer
2
Vous m'avez eu à "C'est tout ce que vous devez savoir [...]. Cependant ...". :-) Git est plein de choses comme celle-ci où une notation et une terminologie similaires signifient des choses différentes dans différents contextes; merci d'avoir si bien clarifié cela.
ShreevatsaR
Merci d'avoir mentionné la liste des rév. Je suis tombé sur cette question en cherchant un moyen de faire ce que fait rev-list via rev-parse.
Mad Physicist
"En d'autres termes, git diff foo..barc'est exactement le même que git diff foo bar; les deux vous montreront la différence entre les extrémités des deux branches foo et bar." Qu'entendez-vous exactement par «différence entre les pointes des deux branches»?
Asad Moosvi
60

Ma version consolidée du .. vs ... avec diff vs log

Diff vs Log & .. vs ..

DauphinDream
la source
3
ce serait très bien, si seulement il n'y avait pas autant de couleurs différentes et d'opérations de configuration mélangées avec ../ ...stuff. Par exemple, log A...Bil n'est pas clair si la commande renvoie l'intersection (partie blanche du diagramme) ou le reste de l'union AB (vert). Ce serait plus pertinent sans opérandes définis et avec une seule couleur.
xealits
1
Doit-il vraiment être diff A..B<—> log A...B, c'est-à-dire que diffère- t-il vraiment avec 2 points, correspond-il à log avec 3 (!) Points? Ou y a-t-il une faute de frappe dans l'image. En regardant comment les points sont codés par couleur, il me semble qu'il y a une faute de frappe dans l'image. Le coin inférieur gauche: log A...Bdevrait être log A..B, à droite (?). Et le journal juste à droite ne devrait ...pas l' être ...
KajMagnus
1
Salut DolphinDream, merci pour votre silhouette. Je l'utilise comme référence ici: gitlab.com/tortoisegit/tortoisegit/issues/3427#note_227200695
Yue Lin Ho
1
@KajMagnus en fait, les couleurs rouge / bleu sont juste utilisées pour faire la distinction entre 2 points et 3 points (indépendamment du fait qu'ils soient utilisés avec diff ou log). Le diagramme est correct. Dans la première colonne, le résultat de diff avec 2 points est similaire au log avec 3 points (d'où tout le diagramme des objectifs pour commencer). Le diff avec 2 points donne les changements de code dans les deux tours jusqu'au point de divergence (illustré par les bulles vertes autour des commits et les parties vertes des diagrammes de van) tandis que le journal avec 3 points donne les journaux de changement (messages de commit) dans les deux tours jusqu'au point de divergence.
DolphinDream
28

git diff foo master Différence entre les commits supérieurs (head) de foo et master.

git diff foo..master Une autre façon de faire la même chose.

git diff foo...masterDiffère de l'ancêtre commun ( git merge-base foo master) de foo et master à la pointe de master. En d'autres termes, affiche uniquement les changements que la branche master a introduits depuis son ancêtre commun avec foo.

Cet exemple de GitHub explique quand utiliser les deux:

Par exemple, si vous créez une branche 'dev' et ajoutez une fonction à un fichier, puis revenez à votre branche 'master' et supprimez une ligne du README, puis exécutez quelque chose comme ceci:

$ git diff master dev

Il vous indiquera qu'une fonction a été ajoutée à partir du premier fichier et qu'une ligne a été ajoutée au README. Pourquoi? Parce que sur la branche, le README a toujours la ligne d'origine, mais sur 'master' vous l'avez supprimée - donc comparer directement les instantanés ressemble à 'dev' l'a ajouté.

Ce que vous voulez vraiment comparer, c'est ce que «dev» a changé depuis que vos branches ont divergé. Pour ce faire, Git a un petit raccourci sympa:

$ git diff master...dev
manojlds
la source
2
git diff foo ... master changements que la branche master a introduits depuis son ancêtre commun avec foo
0fnt
@manojlds ok, question si différente, si vous êtes à la branche dev et que vous validez vos modifications (la fonction) et que vous les transférez dans une branche de développement distante, cela signifie-t-il que le changement visible est uniquement la fonction ou la fonction et le readme?
David
Si je ne me trompe pas, la demande de tirage diff de GitHub utilise le triple point. Est-ce correct?
Shaun Luttin
Lien rompu vers la page d'exemple GitHub.
K.-Michael Aye
6
git diff foo master

montrera les différences entre le sujet et la branche principale à ce moment-là

git diff foo..master

cela montrera également les différences entre le sujet et la branche principale à ce moment-là

git diff foo...master

cela montrera toutes les différences entre le moment où le sujet a été créé à partir de la branche et après

donc les 2 premières commandes sont les mêmes et la dernière montre juste une vue plus large dans l'historique des différences

italiano40
la source
1

arbre de log git

L'image du haut est équivalente à l'arborescence du graphique du bas

A0 <- A1 <- A2 <- A3 (master)
   \
    C0 <- C1 (test)

Une image vaut mille mots, la différence .. ... ^est indiquée ci-dessous.

$ git log master..test
# output C0 C1

$ git log ^master test
# output C0 C1

$ git log master…test
# output A1 A2 A3 C0 C1
yanhaijing
la source