“ การแตกแขนงฟรี” หมายความว่าอย่างไรใน Git


27

"การแตกแขนงฟรี" หมายความว่าอย่างไรใน Git

ฉันได้ยินเรื่องนี้บ่อยมากเมื่อพูดถึง Git เมื่อเปรียบเทียบกับระบบควบคุมเวอร์ชันอื่น

ฉันไม่ได้มีโอกาส (?) ที่จะจัดการกับผู้อื่น ( SVNและอื่น ๆ ) ดังนั้นการแยกสาขา "แพง" ในผู้อื่นเป็นอย่างไร

คำตอบ:


28

การอ้างว่า "การแตกแขนงเป็นอิสระในคอมไพล์" เป็นการทำให้เข้าใจได้ง่ายเพราะไม่ใช่ "ฟรี" ต่อ se มองภายใต้ประทุนการเรียกร้องที่ถูกต้องมากขึ้นจะแตกแขนงที่จะพูดว่าเป็นredonkulouslyราคาถูกแทนเพราะสาขามีพื้นการอ้างอิงถึงการกระทำ ฉันกำหนด "ความเลว" ที่นี่เนื่องจากค่าใช้จ่ายน้อยลง

ลองขุดดูว่าทำไม Git ถึง "ถูก" โดยตรวจสอบว่ามีค่าใช้จ่ายประเภทใด:

มีการใช้กิ่งใน git อย่างไร

ที่เก็บ git .gitส่วนใหญ่ประกอบด้วยไดเรกทอรีที่มีไฟล์ที่มีข้อมูลเมตาที่ git ใช้ เมื่อใดก็ตามที่คุณสร้างสาขาด้วยคอมไพล์เช่นgit branch {name_of_branch}มีบางสิ่งเกิดขึ้น:

  • มีการสร้างการอ้างอิงไปยังสาขาท้องถิ่นที่: .git/refs/heads/{name_of_branch}
  • บันทึกประวัติถูกสร้างขึ้นสำหรับสาขาท้องถิ่นที่: .git/logs/refs/heads/{name_of_branch}

โดยพื้นฐานแล้วไฟล์ข้อความจะถูกสร้างขึ้นสองไฟล์ หากคุณเปิดการอ้างอิงเป็นไฟล์ข้อความเนื้อหาจะเป็น id-sha ของการกระทำที่สาขาชี้ไปที่ โปรดทราบว่าการแตกสาขาไม่ต้องการให้คุณทำการใด ๆเนื่องจากเป็นวัตถุประเภทอื่น ทั้งสองสาขาและการกระทำนั้นเป็น "พลเมืองชั้นหนึ่ง" ในระบบคอมไพล์และวิธีหนึ่งคือคิดถึงความสัมพันธ์ระหว่างสาขาถึงการกระทำโดยรวมมากกว่าการจัดองค์ประกอบ หากคุณลบสาขาการกระทำจะยังคงมีอยู่ว่า หากคุณนำสาขาออกโดยไม่ได้ตั้งใจคุณสามารถลองหาคำสั่งด้วยgit-lost-foundหรือgit-fsck --lost-foundสร้างสาขาบน sha-id ที่คุณพบว่าค้างอยู่ (และตราบใดที่ git ยังไม่ได้ทำการรวบรวมขยะ)

ดังนั้นคอมไพล์จึงติดตามสาขาที่คุณกำลังทำอยู่ได้อย่างไร? คำตอบนั้นอยู่ที่.git/HEADไฟล์ซึ่งมีลักษณะเช่นนี้หากคุณอยู่ในmasterสาขา

ref: refs/heads/master

การสลับสาขาเพียงแค่เปลี่ยนการอ้างอิงใน.git/HEADไฟล์จากนั้นดำเนินการเปลี่ยนแปลงเนื้อหาของเวิร์กสเปซของคุณด้วยสิ่งที่กำหนดไว้ในคอมมิท

สิ่งนี้เปรียบเทียบกับระบบควบคุมเวอร์ชันอื่น ๆ ได้อย่างไร?

ในการโค่นล้มสาขาไดเรกทอรีเสมือนในพื้นที่เก็บข้อมูล ดังนั้นวิธีที่ง่ายที่สุดในการแยกสาขาคือทำจากระยะไกลด้วยสายการบินsvn copy {trunk-url} {branch-url} -m "Branched it!"เดียว SVN จะทำอะไรต่อไปนี้:

  • คัดลอกไดเรกทอรีต้นทางเช่นtrunkไปยังไดเรกทอรีเป้าหมาย
  • ยอมรับการเปลี่ยนแปลงเพื่อทำให้การคัดลอกเสร็จสมบูรณ์

คุณจะต้องดำเนินการนี้จากระยะไกลบนเซิร์ฟเวอร์เนื่องจากการทำสำเนาภายในเครื่องนั้นเป็นการดำเนินการเชิงเส้นเวลาโดยมีไฟล์ที่ถูกคัดลอกและเชื่อมโยง นี่เป็นการดำเนินการที่ช้ามากในขณะที่ทำบนเซิร์ฟเวอร์เป็นการดำเนินการเวลาคงที่ โปรดทราบว่าแม้เมื่อทำการแยกสาขาบนเซิร์ฟเวอร์ย่อยการโค่นล้มต้องใช้การส่งข้อมูลเมื่อทำการแยกในขณะที่ git ไม่ได้ซึ่งเป็นความแตกต่างที่สำคัญ นั่นเป็นค่าใช้จ่ายประเภทหนึ่งที่ทำให้ SVN ราคาถูกน้อยกว่า Git

คำสั่งสำหรับการเปลี่ยนสาขาใน SVNคือsvn switchเป็นจริงsvn updateในการปลอมตัว ขอบคุณแนวคิดไดเรกทอรีเสมือนคำสั่งมีความยืดหยุ่นใน svn มากกว่าในคอมไพล์ ไดเร็กทอรีย่อยในเวิร์กสเปซของคุณสามารถเปลี่ยนเป็นมิเรอร์ url ที่เก็บอื่นได้ สิ่งที่ใกล้เคียงที่สุดคือการใช้git-submoduleแต่การใช้ที่ค่อนข้างแตกต่างจากการแยกสาขา น่าเสียดายที่นี่ยังเป็นการตัดสินใจออกแบบที่ทำให้การสลับช้าลงเล็กน้อยใน SVN กว่าใน Git เนื่องจากต้องตรวจสอบทุกไดเรกทอรีพื้นที่ทำงานที่มี URL ระยะไกลเป็นมิเรอร์ จากประสบการณ์ของผม Git นั้นเปลี่ยนเร็วกว่า SVN เร็วกว่า

การแตกแขนงของ SVN นั้นมาพร้อมกับค่าใช้จ่ายเพราะมันจะทำการคัดลอกไฟล์ ในคอมไพล์ตามที่อธิบายไว้ข้างต้นสาขาคือ "เพียงแค่การอ้างอิง" และสามารถเก็บไว้ในพื้นที่เก็บข้อมูลในท้องถิ่นของคุณและถูกเผยแพร่ตามดุลยพินิจของคุณ จากประสบการณ์ของฉันอย่างไรก็ตาม SVN ยังมีราคาถูกกว่าและมีประสิทธิภาพมากกว่าเช่น ClearCase

เป็นเพียงคนเกียจคร้านที่ SVN ไม่ได้กระจายอำนาจ คุณสามารถมีที่เก็บหลายแห่งเป็นมิเรอร์ไปยัง repo บางแหล่ง แต่การซิงค์การเปลี่ยนแปลงที่แตกต่างกันหลายที่เก็บ SVN นั้นเป็นไปไม่ได้เนื่องจาก SVN ไม่มีตัวระบุที่ไม่ซ้ำสำหรับ commits (git มีตัวระบุแฮชที่อิงเนื้อหาของ เหตุผลที่ว่าทำไมผมเองเริ่มใช้คอมไพล์มากกว่า SVN แต่เป็นเพราะการเริ่มต้นการเก็บข้อมูลเป็นอย่างน่าทึ่งง่ายและราคาถูกในการคอมไพล์ แนวคิดในแง่ของการจัดการการกำหนดค่าซอฟต์แวร์สำเนาที่ต่างกันของโครงการ (โคลน, ส้อม, เวิร์กสเปซหรืออะไรก็ตาม) คือ "สาขา" และคำศัพท์นี้ทำให้การสร้างสำเนาใหม่ใน SVN นั้นไม่ถูกเท่า Git สาขา "ในตัว"

เป็นอีกตัวอย่างหนึ่งในMercurial การแตกแขนงเริ่มแตกต่างกันเล็กน้อยในรูปแบบ DVCS และการสร้าง / ทำลายกิ่งที่มีชื่อจะต้องแยกออกจากกัน ผู้พัฒนา Mercurial นำไปใช้ในภายหลังในการพัฒนาบุ๊กมาร์กเพื่อเลียนแบบรูปแบบการแยกสาขาของ git แม้ว่าheadsจะถูกเรียกtipsและbranchesอยู่bookmarksในคำศัพท์ของ mercurial แทน


ว้าว. ขอบคุณมากสำหรับคำอธิบาย "แพง"
laggingreflex

2
จากแหล่งที่มาของคุณ: This command causes a near-instantaneous commit in the repository, creating a new directory in revision 341. The new directory is a copy of /calc/trunk.- การสร้างสาขานั้นเป็นเรื่องเล็กน้อยใน SVN เว้นแต่คุณจะทำสำเนาทุกไฟล์อย่างชัดเจน
Bobson

@ Bobon ฉันกำลังคิดเกี่ยวกับการเขียนบิตในการแยกอีกครั้งเนื่องจากฉันทำด้วยมือมากมายเกี่ยวกับเรื่องนั้น แต่ประเด็นของฉันยังคงอยู่ที่ความมุ่งมั่นที่จะต้องสร้างสาขาใน Git ไม่ใช่ จากประสบการณ์ที่อ่อนน้อมถ่อมตนของฉันฉันยังคงรู้สึกว่าการเปลี่ยนสาขาใน SVN นั้นช้ากว่าใน Git แต่ฉันไม่สามารถชี้เหตุผลเฉพาะได้ว่าทำไม
Spoike

2
@Spoike - การสับเปลี่ยนแน่นอน และจำเป็นต้องมีการกระทำ ฉันได้ทำการแก้ไขเพื่อชี้แจงบิตที่ฉันมีปัญหา อย่าลังเลที่จะเปลี่ยนกลับหากคุณต้องการ
Bobson

20

ต้นทุนที่แท้จริงของสาขากำลังรวมเข้าด้วยกัน Git ทำให้ง่ายกว่าระบบควบคุมแหล่งอื่น ดูคำถาม Stack Overflow อย่างไรและ / หรือทำไมการผสานใน Git ดีกว่าใน SVN .


5
อย่างเคร่งครัด Git เพียง แต่ทำให้มันง่ายกว่าที่บาง SCMs อื่น ๆ
Donal Fellows

10

ใน Git สาขาจะมีการอ้างอิงถึงคอมมิชชันต่อ repo ท้องถิ่น สร้างมันราคาถูกมากไม่มีเครือข่ายเลย ไม่ฟรี (คุณต้องพิมพ์คำสั่ง) แต่ให้ตายเถอะ

การแตกแขนงไม่ได้แพงมากใน SVN แต่เป็นเพียงแค่สำเนาซึ่งเป็นการกระทำที่ราคาถูกมาก SVN มีโมเดลพื้นที่เก็บข้อมูลส่วนกลางดังนั้นจึงเป็นการเข้าถึงเครือข่าย แต่ไม่ใช่รุ่นที่น่ากลัว

ในทางกลับกัน CVS ในทางกลับกันการแตกแขนงนั้นมีราคาแพงมาก โดยทั่วไปแล้วสาขา CVS เกี่ยวข้องกับการเพิ่มแท็ก แต่ใน CVS ซึ่งหมายความว่าทุกไฟล์ที่ได้รับผลกระทบจะต้องมีการแก้ไข แต่ละไฟล์ถูกเขียนใหม่เพื่อรวมแท็กใหม่ มันมีราคาแพงมาก และถ้าที่เก็บของคุณใหญ่มันก็ช้าเหมือนกัน อันที่จริงถ้าคุณอยู่ในโครงการขนาดใหญ่มันช้าพอที่คนบางคนมักจะหลีกเลี่ยงการสร้างสาขาหากพวกเขาทำได้


4
ด้วย Git มันยิ่งน้อยกว่าความมุ่งมั่น - สาขาเป็นเพียงฉลาก และ SVN ฟังดูมีราคาแพงกว่า CVS เนื่องจากทั้งคู่คัดลอกไฟล์ทั้งหมด
Izkata

8
@Izkata: หากเราเห็นจากมุมมองของผู้ใช้ - ใช่ไฟล์ทั้งหมดจะถูกคัดลอกจากมุมมองการนำไปใช้ (และประสิทธิภาพ) - ไม่เพียงเพิ่มเรคคอร์ดเกี่ยวกับการคัดลอก
maxim1000

@Izkata มากเกินไปที่จะแสดงความคิดเห็น - ดูคำตอบของฉัน
gbjbaanb

6
@Izkata SVN สร้างตัวชี้และการอ้างอิงมันไม่ได้คัดลอกทุกอย่าง
Aaron McIver

2
สาขา Git ไม่ใช่การกระทำมันเป็นเพียงการอ้างอิงถึงการกระทำที่สามารถเคลื่อนย้ายไปมาได้อย่างอิสระกับการกระทำอื่น ๆ คิดว่า repo Git เป็นเพียงต้นไม้แห่งความมุ่งมั่นและกิ่งก้านเป็นโน้ตที่สามารถย้ายไปรอบ ๆ ได้อย่างอิสระบนต้นไม้ต้นนั้น
40XUserNotFound

5

การแยกสาขาของ SVN นั้นฟรีเท่ากับของ Git มันเป็นเพียงข้อมูลการดูแลเล็กน้อยที่บอกว่าสาขาเริ่มต้นจากที่ไหนไม่มีการเปลี่ยนแปลงไฟล์ที่เก็บไว้ แต่อย่างใด 'คัดลอก' ใน SVN เหมือนกับการเพิ่ม symlink ไปยังไดเรกทอรี Unix โปรดทราบว่าสาขา SVN จะไม่ต้องใช้การเดินทางผ่านเครือข่ายจนกว่าคุณจะยอมรับการเปลี่ยนแปลงสำเนาการทำงานของคุณ (แต่มีจุด SCM ไม่มากนักหากคุณไม่ได้กระทำการนอกพื้นที่ในบางจุด)

โปรดทราบว่าสาขา Git จะเกี่ยวข้องกับการดูแลรักษาบางอย่างเช่นการเพิ่มแท็กนั้นไว้ภายในซึ่งจะต้องถูกเก็บไว้ที่ใดที่หนึ่งเมื่อคุณส่งมอบ มันไม่ใช่เรื่องใหญ่เลยซึ่งเป็นเหตุผลว่าทำไมมันถึงเรียกว่า 'ฟรี'


5

มันเป็น 'ฟรี' (ในบริบทนี้ 'ฟรี' จริงๆหมายถึงความรวดเร็วและไม่ต้องเสียพื้นที่) เพราะในระบบควบคุมเวอร์ชันเก่าบางสาขาสาขาก็เป็นสำเนาที่สมบูรณ์ของรหัส ณ จุดนั้นดังนั้นสาขาจึงใช้เวลามาก พื้นที่และเป็นเรื่องง่ายที่จะจบลงด้วยซอฟต์แวร์เวอร์ชั่นเต็มรูปแบบที่แตกต่างกันจำนวนมากที่วางอยู่รอบ ๆ ในที่อื่น ๆ มันไม่ได้เป็นสำเนาที่สมบูรณ์ของรหัส แต่ทุกไฟล์ยังคงต้องมีการแก้ไขสำหรับแท็กดังนั้นจึงช้าและเจ็บปวด ('แพง')

กิ่งก้านของ git นั้นเป็นฉลากที่ชี้ไปที่การคอมมิทและหลีกเลี่ยงปัญหาข้างต้น


1

อีกแง่มุมหนึ่งของ "ฟรี / ราคาถูก / แพง" ก็คือต้นทุนของนักพัฒนาในการจัดการกับผลที่ตามมาจากการแตกสาขา; เช่นกระบวนการของการรวมการเปลี่ยนแปลงจากสาขา

และที่นี่การรวมสาขาในระบบ DVCS เช่น Git และ Mercurial นั้นง่ายกว่าในระบบเก่า ... เพราะระบบ DVCS นั้นทำงานได้ดีกว่ามากในการติดตามประวัติของเวอร์ชันในกราฟ เช่นที่การแตกแขนงก่อนหน้านี้มีการรวมกันเกิดขึ้น สิ่งนี้ทำให้การผสานมีความแม่นยำยิ่งขึ้นลดความขัดแย้งที่ไม่จำเป็นและ ... ทำให้การผสาน "ง่ายขึ้น" หรือ "น่ากลัวน้อยลง" สำหรับผู้พัฒนาที่เกี่ยวข้อง

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.