9

我对 mercurial 很陌生,我已经阅读了很多关于这个主题的内容,但我一直无法找到明确的答案。

反复无常的指南说:“为了提高效率,只要源和目标位于同一文件系统上,就使用硬链接进行克隆(请注意,这仅适用于存储库数据,不适用于工作目录)。”

存储库wiki 页面说:“与存储库根目录中的 .hg 目录共存的所有文件和目录都被认为存在于工作目录中”。

现在,要在主仓库中“链接”一个子仓库,我会这样做:

hg init main
cd main
echo subrepo = ../subrepo > .hgsub
hg clone ../subrepo subrepo           # (1)
hg add
hg ci -m "initial rev of the main repo"

上面的定义是否意味着我实际上是在执行 (1) 时创建一个副本??subrepo还是我只是创建一个符号链接../subrepo?根据 的输出ls,它是一个实际的副本。但这对我来说听起来很奇怪......如果有人可以对这个主题有所了解,我将不胜感激。

4

2 回答 2

6

首先,Mercurial的那部分,我不是专家,但这是我所理解的。

不,您没有创建指向整个目录的链接。相反,文件在其中被硬链接。

这意味着磁盘上的空间被保留以保持您的目录结构分开,但文件都是相同的,因为它们只是被克隆,所以它们被构造为返回原始文件的链接。

当您通过addor commit( ci) 命令开始操作存储库时,Mercurial 会破坏硬链接,并根据需要为每个文件构建单独的文件。

现在,这纯粹是一个技术性的东西,你不需要知道或关心这个。如果它更容易,只需将克隆视为原始存储库的完整副本,单独的文件等等。硬链接部分只是为相同的东西节省磁盘空间。

由于一个典型的项目有很多文件,而一个典型的变更集只更改了几个文件,而克隆的一个典型原因是您要进行一组固定的更改,因此硬链接是有意义的,因为存储库目录中的许多文件在存储库的生命周期内,将与它们的原始版本 100% 相同。

对于那些不是,所有这一切都由 Mercurial 默默地为您处理。

于 2010-12-08T18:44:59.303 回答
2

让我们先看看当你克隆时会发生什么,而不讨论子存储库。当你这样做

$ hg clone A B

然后 Mercurial 将为里面的文件建立硬链接A/.hg/store/data。因此,如果跟踪了一个名为的文件x,那么在克隆之后你会看到

A/.hg/store/data/x.i

B/.hg/store/data/x.i

是硬链接的——这意味着这两个文件名实际上是指同一个文件。正如 Lasse 指出的那样,这很聪明,因为您可能永远不会对x克隆进行更改,因此没有理由为和克隆创建两个不同x.i的文件。另一个优点是创建硬链接比复制文件要快得多,尤其是在文件非常大的情况下:硬链接是一个常数时间的操作。ABx.i

在上面的示例中,您正在向存储库添加一个子subrepo存储main库。子存储库由两部分组成:

  1. 子存储库本身。这是你在做的时候创造的

    $ hg clone ../subrepo
    
  2. 子存储库元数据。这是您存储在.hgsub文件中的内容。您必须告诉 Mercurial 您想要子存储库的位置以及 Mercurial 可以从哪里克隆它。

您询问是否复制或符号链接存储库,并且您肯定复制(克隆)它,正如您也已确认ls. 之后,您向 Mercurial 添加了一些元数据,告诉它可以在哪里找到子存储库。这与普通文件系统意义上的符号链接无关,它只是 Mercurial 的一些元数据。

于 2010-12-09T12:29:25.540 回答