12

我是GitX的作者。GitX 的功能之一是分支的可视化,可以在这里看到。

这种可视化当前是通过读取从 git 以正确顺序发出的提交来完成的。对于每个提交,父母都是已知的,因此以正确的方式建立通道相当容易。

我想通过使用我自己的提交池并自己线性化提交来加快这个过程。这允许我重用现有的已加载提交并允许 git 更快地发出提交,因为它不必以正确的顺序发出它们。

但是,我不确定使用什么算法来实现这一点。重要的是构建是增量的,因为提交的加载可能需要很长时间(100,000 次提交超过 5 秒,应该全部显示)。

Gitk 也是如此,这里有一个补丁说明了它是如何实现的,但是我的 TCL 技能很弱,而且补丁的注释不是很彻底,而且有点难以理解。

我还希望这个算法高效,因为它必须处理数十万次提交。它还必须显示在表格中,因此快速访问特定行很重要。

我将描述到目前为止的输入、我想要的输出和一些观察结果。

输入:

  • 我有一个哈希表形式的当前提交池,将提交 ID 映射到提交对象。此池不必是完整的(具有所有必要的提交)
  • 我在 git 的新提交中加载了一个单独的线程,每次加载新提交时都可以调用一个回调。没有保证提交的顺序,但在大多数情况下,下一个提交是前一个提交的父级。
  • 一个提交对象有自己的修订 id 和所有其父对象的修订 id
  • 我有一个应该列出的分支负责人列表。也就是说,没有应该显示的 DAG 的单个“顶部”。也不必有单个图根。

输出:

  • 我需要按拓扑顺序线性化这些提交。也就是说,一个提交在其父项被列出之后不能被列出。
  • 我还需要可以在上面的屏幕截图中看到的“分支线”。这些可能需要预先计算,因为它们中的大多数依赖于他们的孩子。

几点说明:

  • 有必要重新定位提交列表。例如,我们可能必须提交不相关的提交(分支头),直到出现使一个头成为另一个头的祖先的提交。
  • 必须显示多个分支提示
  • 重要的是这个过程是增量的,以便在数据仍在加载时至少有部分视图可用。这意味着必须在中途插入新数据并且必须重新调整分支线。
4

4 回答 4

6

标准的拓扑排序是 O(n)(OK,O(V+E)),即您应该能够在几分之一秒内对内存中的一百万次提交进行排序。不需要像 Tcl 中那样的增量 hack。

顺便说一句,我每天都使用 GitX(在 OS X 上看起来比 Gitk 好得多)并且没有任何问题(可能是因为我的存储库中没有那些疯狂的合并):)

于 2009-04-03T02:46:01.893 回答
3

好的,所以我在阅读整个补丁时也遇到了同样的困难,但让我们看看我是否可以根据我的想法把它拼凑起来。

首先,gitk 通过将一串提交压缩成一个弧来简化事情,其中​​包含一系列提交,每个提交只有一个父节点和一个子节点。除了其他任何事情之外,这样做应该会大大减少您必须为排序考虑的节点数量,这将有助于您使用的任何算法。作为奖励,相关的提交最终将组合在一起。

当您阅读新提交时,这确实会在查找弧方面引入一些复杂性。有几种情况:

  • 新的提交有一个单亲,或者没有双亲。它延伸了一个(可能是空的)弧。大多数情况下,您只需扩展最近的弧。有几个有趣的子案例:
    • 如果它的父级已经有一个子级,它可能会导致现有的弧被分割(即,它的父级结果是一个分支点,我猜你不知道提前知道)。
    • 它可能是将两条弧线连接在一起的“缺失环节”。
    • 你可能已经知道这个提交有多个孩子
  • 新提交有多个父项(合并提交)。

您可能希望在弧中包含多子或多父提交,或者将它们分开可能更有意义。无论哪种方式,逐步建立这组弧应该不会太难。

一旦你有了这些弧线,你仍然需要尝试将它们线性化。在您的情况下,上述维基百科页面上描述的第一个算法听起来很有用,因为您有一组已知的分支点可用作您的初始集合 S。

其他注意事项:

  • 重定位提交应该是可管理的。首先,你只需要在连接两条弧时关心,要么通过新的合并提交,新发现的分支点,要么将两条弧合二为一。任何给定的弧都可以轻松地维持其当前的行号范围(假设您可以将弧放在连续的行上),因此遍历树检查所有新祖先是否稍后出现应该很快。
  • 关于绘制图形线我知道的不多,但我想它与您现在所做的不会有太大不同。

无论如何,我希望这会有所帮助。至少想想很有趣。

于 2009-04-04T22:09:11.463 回答
0

你真的需要一次显示 100k 提交吗?什么样的用户可以吸收这种信息?

你有没有考虑分页?即只计算〜100次提交或其他东西。如果分支线返回(页外),您可以使用 Github 的反向箭头之类的东西来显示。

于 2009-04-09T11:36:23.317 回答
-2

我没有使用 GitX,所以也许我遗漏了一些东西,但似乎你可以从每个当前分支的头部从孩子走到父母,直到你可以绘制几个屏幕的图表。

这可能不会为您提供较早扎根的分支的最佳视觉布局。但似乎响应能力比等待绘制具有最少交叉点的图表更重要,因为大多数用户可能对最近的活动感兴趣。

于 2009-03-31T18:17:18.907 回答