Search 二进制搜索或Btree索引更新问题

Search 二进制搜索或Btree索引更新问题,search,tree,binary-search-tree,binary-search,b-tree,Search,Tree,Binary Search Tree,Binary Search,B Tree,想象一下,你每天都收到一位作家的新书。 这本书正在进行中。 他没有告诉你他改变或增加了什么 您的工作是识别更改和添加内容,并仅将这些内容传递给出版商(出版商每天没有时间阅读整本书) 为了解决这个问题,这本书由100万行ascii文本组成,并且不断增长(实际上是一个MySQL备份文件) 我目前的想法是对每一行(1k个字符)进行安全哈希(例如SHA256),并将其存储在HD上。因为散列值只有32字节,所以文件只有32MB 然后,当我们明天得到下一个文件时,我们逐行检查它,为每一行创建一个新的哈希,并

想象一下,你每天都收到一位作家的新书。 这本书正在进行中。 他没有告诉你他改变或增加了什么

您的工作是识别更改和添加内容,并仅将这些内容传递给出版商(出版商每天没有时间阅读整本书)

为了解决这个问题,这本书由100万行ascii文本组成,并且不断增长(实际上是一个MySQL备份文件)

我目前的想法是对每一行(1k个字符)进行安全哈希(例如SHA256),并将其存储在HD上。因为散列值只有32字节,所以文件只有32MB


然后,当我们明天得到下一个文件时,我们逐行检查它,为每一行创建一个新的哈希,并将其与前一天的哈希进行比较

当这个过程完成后,我们将覆盖哈希文件,以备第二天使用

比较使用字符串比较(><操作数)的二进制搜索方法 这将返回平均四次迭代的结果

我还没有编写一个btree索引解决方案,但您将如何处理这个问题呢?

我将使用

如果我需要在我自己的程序中实现它,我会使用其中一种算法来查找两个序列中的一个,将每个文件视为一个行序列。

“然后当我们明天得到下一个文件时,我们逐行检查它,为每一行创建一个新的哈希,并将其与前一天的哈希进行比较。”

明白了:今天的哈希值有一百万行,而昨天的哈希值有一百万行

是否插入或删除行?如果不是,这是一组简单的并行读取,以查看散列是否不同

如果存在添加或删除,则必须使用diff算法来确定更改的范围

没关系。不太难实施

在这种情况下,以下内容毫无意义

比较使用二进制搜索 字符串比较的方法(>< 操作数)这将在 四次迭代的平均值


散列值是否有某种排序?或者某种树形结构?

一本100万行的书是巨大的:每页可能有30-50行,所以让我们慷慨地假设每页100行,这意味着书中有10000页

1KB的行也比正常的行大得多;基本的可读性表明,每行的字符数远远不够。您打算散列最大为1KB的行,还是将文件分为1KB的块?您的方案的一个问题是,任何重复的行都会有重复的散列;您永远无法确定其中一行是何时添加或删除的

您可能还需要将删除的行通知发布者

与Glomek一样,我会在文件上使用
diff
。如果将文件置于RCS或CVS控制之下,则只会存储文件的当前版本以及先前版本之间的差异。有了这个,您也可以提供一周或一个月的累计差异


我可能不会开发自己的B树索引。

您描述的解决方案与rsync算法有些相似。重要的一点是,rsync必须识别目标文件中任何位置的现有块,即与原始文件的任何偏移量

如果您的文件是真正的记录结构,您可以像您建议的那样进行简化。如果没有,则需要滚动校验和

此外,您是否必须识别重新排序?还是仅插入/删除/替换

最常见的情况是完全rsync算法,如下所示:

  • 参数定义:

  • 选择大小为512或1k的块通常可以正常工作。
    • 选择“强”校验和。类似于MD4之类的东西。64位就足够了
    • 选择“弱”滚动校验和。一种允许您“减”尾字节并“加”头字节以获得前向1字节块的校验和的方法。通常16位校验和工作正常
  • 旧文件的签名:

  • 遍历整个旧文件,在每个块计算弱和强校验和。具有16位和64位校验和,以及512字节的块,即每块10字节,或每兆20KB。这是“签名”
  • 使用新文件和旧文件的签名创建“修补程序”:

  • 加载旧文件的签名,最好是一个哈希表,以弱校验和为键,强校验和和和块位置为值。
    • 读取新文件的第一个块
    • 计算加载块的弱校验和
    • 检查哈希表以查看是否存在弱校验和
    • 如果找到,计算强校验和,并与哈希中找到的校验和进行比较
    • 如果两个校验和都匹配,则在散列中用块引用标记为“got it”,前进一整块大小并返回步骤3
    • 如果强校验和不匹配,或者弱校验和不在散列中,则“滚动”弱校验和,即“添加”块后的下一个字节,并从尾部“减去”第一个字节
    • 将尾部的“substracted”字节添加到修补程序中的“new”字节列表中
    • 返回到步骤4
  • 将修补程序应用于旧文件

  • “补丁”是滚动校验和时丢失的“新”字节列表,加上与旧文件匹配的“got it”块列表

这是一种用于在数据仓库上运行的技术。在无法识别源系统中已更改数据的情况下,可以获取数据的快照,并将其与上次快照进行比较,以识别差异。这项技术甚至在中得到提及,并在中使用

您需要一个具有非常宽密钥的哈希算法,因为这种方法容易受到攻击。MD5或SHA家族的任何成员都可以。它也无法在没有经过th的post过程的情况下检测删除