อะไรคือความแตกต่างระหว่าง double-dot“ .. ” และ triple-dot“ …” ใน Git diff commit


190

อะไรคือความแตกต่างระหว่างคำสั่งต่อไปนี้:

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

คู่มือต่างต่างพูดถึงมัน:

เปรียบเทียบสาขา

$ git diff topic master    <1>
$ git diff topic..master   <2>
$ git diff topic...master  <3>
  1. การเปลี่ยนแปลงระหว่างเคล็ดลับของหัวข้อและสาขาหลัก
  2. เช่นเดียวกับข้างต้น
  3. การเปลี่ยนแปลงที่เกิดขึ้นในสาขาหลักตั้งแต่เมื่อเริ่มหัวข้อสาขา

แต่ไม่ชัดเจนสำหรับฉันเลย


ขณะที่คำถามไม่ได้ซ้ำคำตอบนี้แสดงให้เห็นว่ามีภาพกราฟิกความหมายของ..และ...ในและความหมายที่แตกต่างกันของพวกเขาในgit diff git log
Mark Longair

คำตอบ:


335

ตั้งแต่ผมต้องการสร้างภาพเหล่านี้ผมคิดว่ามันอาจจะมีมูลค่าการใช้พวกเขาในคำตอบอื่นแม้ว่ารายละเอียดของความแตกต่างระหว่าง..(dot-dot) และ...(จุดจุดจุด) เป็นหลักเช่นเดียวกับในคำตอบของ manojlds

โดยgit diffทั่วไปคำสั่ง¹จะแสดงความแตกต่างระหว่างสถานะของแผนภูมิระหว่างสองจุดในกราฟการกระทำ ..และ...สัญลักษณ์ในgit diffมีความหมายต่อไปนี้:

ภาพประกอบของวิธีการต่าง ๆ ในการระบุข้อผูกพันสำหรับคอมไพล์คอมไพล์

กล่าวอีกนัยหนึ่งgit diff foo..barก็เหมือนกับgit diff foo bar; ทั้งสองจะแสดงให้คุณเห็นความแตกต่างระหว่างเคล็ดลับของทั้งสองสาขาและfoo barบนมืออื่น ๆ ที่git diff foo...barจะแสดงให้คุณเห็นความแตกต่างระหว่าง "ฐานผสาน" barของทั้งสองสาขาและเคล็ดลับของ "ฐานผสาน" มักจะกระทำครั้งสุดท้ายเหมือนกันระหว่างสองสาขาดังนั้นคำสั่งนี้จะแสดงการเปลี่ยนแปลงที่งานของคุณbarได้แนะนำขณะที่ไม่สนใจทุกสิ่งที่ทำfooในเวลาเดียวกัน

นั่นคือทั้งหมดที่คุณจำเป็นต้องรู้เกี่ยวกับ..และข้อความใน... git diffอย่างไรก็ตาม ...


... แหล่งที่มาของความสับสนทั่วไปที่นี่คือ..และ...หมายถึงสิ่งต่าง ๆ อย่างละเอียดเมื่อใช้ในคำสั่งเช่นgit logคาดว่าชุดของการกระทำเป็นหนึ่งหรือมากกว่าอาร์กิวเมนต์ (คำสั่งเหล่านี้ทั้งหมดใช้git rev-listเพื่อแยกรายการการคอมมิทจากการขัดแย้ง)

ความหมายของ..และ...สำหรับgit logสามารถแสดงด้วยกราฟดังนี้:

ภาพประกอบแสดงวิธีที่แตกต่างกันในการระบุช่วงของการคอมมิตสำหรับบันทึก git

ดังนั้นgit rev-list foo..barแสดงทุกอย่างในสาขาbarที่ไม่ได้อยู่ในสาขาfooด้วย บนมืออื่น ๆ ที่git rev-list foo...barแสดงให้เห็นว่าคุณกระทำทั้งหมดที่มีทั้งในfoo หรือ barแต่ไม่ใช่ทั้งสองอย่าง แผนภาพที่สามเพิ่งแสดงให้เห็นว่าถ้าคุณแสดงรายการกิ่งไม้ทั้งสองคุณจะได้รับการยอมรับที่อยู่ในหนึ่งหรือทั้งสองอย่าง

ฉันพบว่ามันสับสนเล็กน้อยและฉันคิดว่ากราฟไดอะแกรมช่วยได้ :)

¹ฉันพูดว่า "โดยทั่วไป" เท่านั้นตั้งแต่เมื่อแก้ไขข้อขัดแย้งในการรวมตัวอย่างเช่นgit diffจะแสดงการผสานสามทางให้คุณเห็น


1
ฉันชอบไดอะแกรมของคุณ ฉันขึ้นมาด้วยตัวเองเมื่อไม่นานมานี้เช่นกัน ฉันมีความคิดบางอย่างสำหรับgit diffแผนภาพของตัวเองที่ฉันจะทำในภายหลัง

34
มีคนสังเกตเห็นไหม? ผลกระทบของ..และ...ความรู้สึกย้อนกลับในgit diff(เมื่อเทียบกับgit rev-list)!
Robert Siemer

2
คุณมีฉันที่ "นั่นคือทั้งหมดที่คุณต้องรู้ [... ] อย่างไรก็ตาม ... " :-) Git เต็มไปด้วยสิ่งต่าง ๆ เช่นนี้ที่สัญกรณ์และคำศัพท์ที่คล้ายกันหมายถึงสิ่งที่แตกต่างในบริบทที่แตกต่างกัน; ขอบคุณที่ชี้แจงเรื่องนี้ให้ดี
ShreevatsaR

ขอบคุณที่พูดถึง rev-list ฉันเจอคำถามนี้ในขณะที่มองหาวิธีการทำสิ่งที่ rev-list ทำผ่าน rev-parse
นักฟิสิกส์บ้า

"ในคำอื่น ๆgit diff foo..barเหมือนกันgit diff foo bar; ทั้งสองจะแสดงให้คุณเห็นความแตกต่างระหว่างเคล็ดลับของทั้งสองสาขาฟูและบาร์" คุณหมายถึงอะไรโดย "ความแตกต่างระหว่างเคล็ดลับของทั้งสองสาขา"?
ซาด Moosvi

60

รุ่นรวมของฉัน.. VS ...กับdiff VS บันทึก

Diff vs Log & .. vs ..


3
มันจะดีมากถ้าเพียง แต่มันไม่มีสีที่แตกต่างกันมากมายและตั้งค่าการใช้งานผสมกับ../ ...สิ่งต่าง ๆ ตัวอย่างเช่นlog A...Bมันไม่ชัดเจนว่าคำสั่งส่งคืนจุดตัด (ส่วนสีขาวของไดอะแกรม) หรือส่วนที่เหลือของสหภาพสหภาพ (สีเขียว) มันจะมากขึ้นไปยังจุดที่ไม่มีตัวถูกดำเนินการชุดใด ๆ และมีเพียง 1 สี
xealits

1
นี่ควรเป็นdiff A..B<—> log A...Bหรือไม่นั่นคือแตกต่างจาก 2 จุดจริงหรือไม่และสอดคล้องกับการบันทึกด้วยจุด 3 (!) หรือไม่ หรือมีการพิมพ์ผิดในภาพ ดูว่าจุดต่างๆมีการกำหนดรหัสสีอย่างไรดูเหมือนว่าฉันมีการพิมพ์ผิดในภาพ มุมซ้ายล่าง: log A...Bควรเป็นlog A..Bจริง (?) และเข้าสู่ระบบเพียงเพื่อที่เหมาะสมควรจะเป็นไม่ได้... ..
KajMagnus

1
สวัสดี DolphinDream ขอบคุณสำหรับรูปของคุณ ฉันใช้เป็นข้อมูลอ้างอิงที่นี่: gitlab.com/tortoisegit/tortoisegit/issues/3427#note_227200695
Yue Lin Ho

1
@KajMagnus จริงๆแล้วสีแดง / สีน้ำเงินใช้เพื่อแยกความแตกต่างระหว่าง 2 จุดและ 3 จุด (โดยไม่คำนึงถึงการใช้ diff หรือ log) แผนภาพถูกต้อง ในคอลัมน์แรกผลลัพธ์ของ diff ที่มี 2 จุดคล้ายกับบันทึกที่มี 3 จุด (ดังนั้นแผนภาพวัตถุประสงค์ทั้งหมดจะเริ่มต้นด้วย) diff ที่มี 2 จุดให้รหัสเปลี่ยนแปลงทั้ง revs ลงไปที่จุด divergence (แสดงโดยฟองสีเขียวรอบ commits และส่วนสีเขียวของ van diagrams) ในขณะที่ log ที่มี 3-point ให้บันทึกการเปลี่ยนแปลง (กระทำข้อความ) ใน revs ทั้งสองลงไปที่จุดแตกต่าง
DolphinDream

28

git diff foo master ความแตกต่างระหว่างความมุ่งมั่นด้านบน (หัว) ของ foo และต้นแบบ

git diff foo..master อีกวิธีในการทำสิ่งเดียวกัน

git diff foo...masterแตกต่างจากบรรพบุรุษทั่วไป ( git merge-base foo master) ของ foo และ master จนถึงส่วนปลายของ master ในคำอื่น ๆ แสดงเฉพาะการเปลี่ยนแปลงที่สาขาหลักได้แนะนำมาตั้งแต่บรรพบุรุษร่วมกับ foo

ตัวอย่างจาก GitHub อธิบายว่าเมื่อใดควรใช้ทั้งสอง:

ตัวอย่างเช่นหากคุณสร้างสาขา 'dev' และเพิ่มฟังก์ชั่นให้กับไฟล์จากนั้นกลับไปที่สาขา 'master' ของคุณและลบบรรทัดออกจาก README แล้วรันดังนี้:

$ git diff master dev

มันจะบอกคุณว่ามีการเพิ่มฟังก์ชั่นจากไฟล์แรกและมีการเพิ่มบรรทัดใน README ทำไม? เนื่องจากในสาขา README ยังคงมีบรรทัดดั้งเดิมอยู่ แต่ใน 'master' คุณได้ลบมันออก - ดังนั้นการเปรียบเทียบสแนปชอตโดยตรงจึงดูเหมือนว่า 'dev' เพิ่มเข้าไป

สิ่งที่คุณต้องการเปรียบเทียบจริง ๆ คือสิ่งที่ 'dev' เปลี่ยนไปนับตั้งแต่สาขาของคุณแตกต่าง ในการทำเช่นนั้น Git มีการจดชวเลขเล็กน้อย:

$ git diff master...dev

2
git diff foo ... การเปลี่ยนแปลงหลักที่สาขาหลักได้แนะนำเนื่องจากมันเป็นบรรพบุรุษร่วมกับ foo
0fnt

@manojlds ตกลงคำถามที่แตกต่างกันมากถ้าคุณอยู่ที่สาขา dev และยอมรับการเปลี่ยนแปลงของคุณ (ฟังก์ชั่น) และผลักดันการเปลี่ยนแปลงในสาขา dev ระยะไกลหมายความว่าการเปลี่ยนแปลงที่มองเห็นเป็นเพียงฟังก์ชั่นหรือฟังก์ชั่นและ readme?
David

หากฉันไม่เข้าใจผิดคำขอการดึงของ GitHub จะใช้จุดสามจุด นั่นถูกต้องใช่ไหม?
Shaun Luttin

ลิงก์เสียไปที่หน้าตัวอย่าง GitHub
K.

6
git diff foo master

จะแสดงความแตกต่างระหว่างหัวข้อและสาขาหลัก ณ เวลานั้น

git diff foo..master

สิ่งนี้จะแสดงความแตกต่างระหว่างหัวข้อและสาขาหลักในเวลานั้น

git diff foo...master

สิ่งนี้จะแสดงความแตกต่างทั้งหมดระหว่างเมื่อหัวข้อถูกสร้างขึ้นจากสาขาและหลังจาก

ดังนั้นคำสั่ง 2 คำแรกจะเหมือนกันและคำสั่งสุดท้ายจะแสดงมุมมองที่กว้างขึ้นในประวัติ diff


1

ต้นไม้บันทึกคอมไพล์

ภาพด้านบนเทียบเท่ากับแผนภูมิกราฟด้านล่าง

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

รูปภาพมีค่าหนึ่งพันคำความแตกต่างระหว่าง.. ... ^ดังแสดงด้านล่าง

$ git log master..test
# output C0 C1

$ git log ^master test
# output C0 C1

$ git log master…test
# output A1 A2 A3 C0 C1
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.