Answers:
“分支在git中是免费的”的说法是事实的简化,因为它本身并不是“免费的”。在幕后,更正确的说法是说分支便宜得多,因为分支基本上是对commit的引用。我将“便宜”定义为开销越少越便宜。
让我们通过检查Git有哪些开销来探究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中的“一等公民”,一种方式是将分支与提交的关系视为聚合而不是组合。如果删除分支,则提交仍将以“悬挂”的形式存在。如果您不小心删除了一个分支,则始终可以尝试使用git-lost-found
或查找提交,git-fsck --lost-found
并在sha-id上创建分支,然后发现该分支悬空了(只要git尚未进行任何垃圾收集)。
那么git如何跟踪您正在处理的分支?答案与.git/HEAD
文件有关,如果您在master
分支上,则看起来像这样。
ref: refs/heads/master
切换分支只需更改.git/HEAD
文件中的引用,然后继续使用提交中定义的内容更改工作区的内容。
在Subversion中,分支是存储库中的虚拟目录。因此,最简单的分支方法是使用单线远程进行svn copy {trunk-url} {branch-url} -m "Branched it!"
。SVN将执行以下操作:
trunk
到目标目录,您将需要在服务器上远程执行此操作,因为在本地进行复制是线性时间操作,其中文件被复制和符号链接。这是一个非常慢的操作,而在服务器上执行此操作是固定时间的操作。请注意,即使在服务器上执行分支,在git分支时,subversion仍需要提交,而git则不需要。这是使SVN略低于Git的一种开销。
SVN中用于切换分支的命令(即svn switch
)确实是svn update
伪装的。由于虚拟目录的概念,该命令在svn中比在git中更加灵活。可以切换工作空间中的子目录以镜像另一个存储库URL。最接近的事情是使用,git-submodule
但是使用在语义上与分支完全不同。不幸的是,这也是一个设计决定,使得SVN中的切换比Git中的切换慢一些,因为它必须检查每个工作空间目录所镜像的远程URL。以我的经验,Git比SVN切换分支更快。
SVN的分支需要付出一定的代价,因为它会复制文件,并且始终需要公开发布。如上所述,在git中,分支只是“引用”,可以保留在本地存储库中,并可以自行决定发布。以我的经验,SVN仍然比ClearCase便宜得多,性能也更高。
SVN不分散只是一个遗憾。您可以将多个存储库镜像到某个源存储库,但无法同步不同的更改,因为SVN没有用于提交的唯一标识符(git具有基于提交内容的哈希标识符),因此无法同步多个SVN存储库。我之所以开始在SVN上而不是在SVN上使用git的原因是,在git中启动存储库非常容易且便宜。从软件配置管理的概念上讲,项目的每个不同副本(克隆,派生,工作区或其他内容)都是一个“分支”,并且鉴于此术语,在SVN中创建新副本并不像Git便宜,后者分支“内置”。
作为另一个示例,在Mercurial中,分支开始与DVCS有点不同,并且创建/销毁命名分支需要单独的提交。水银开发商在开发后实现书签来模仿Git的同一分支模型虽然heads
被称为tips
和branches
是bookmarks
不是在善变的术语。
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中创建分支很简单,除非要显式地为每个文件创建一个副本。
分支机构的实际成本正在将其合并。与其他一些源代码控制系统相比,Git使此操作变得更容易。请参阅堆栈溢出问题如何和/或为什么在Git中合并比在SVN中更好?。
在Git中,分支只是引用对本地存储库的提交。创建它非常便宜,根本没有网络。不是很自由(您必须键入命令),但是该死的很近。
在SVN中,分支并不是特别昂贵-只是一个副本,这是非常便宜的提交。SVN确实有一个中央存储库模型,因此它是一种网络访问,但不是可怕的。
另一方面,在古老的CVS中,分支非常昂贵。基本上,CVS分支涉及添加标签,但是在CVS中,这意味着必须修改每个受影响的文件。每个文件都被重写以包括新标签。那太贵了。而且,如果您的存储库很大,它的运行速度也会非常慢。实际上,如果您在进行大型项目,它的运行速度很慢,以至于有些人倾向于避免建立分支机构。