【问题标题】:Using b trees in a database在数据库中使用 b 树
【发布时间】:2013-02-09 06:17:19
【问题描述】:

我必须为一个学校项目使用 b 树实现一个数据库。该数据库用于存储音频文件(歌曲),并且可以进行许多不同的查询,例如询问给定艺术家或特定专辑的所有歌曲。

直观的想法是在b树上为每个字段使用(歌曲、专辑、艺术家...),问题是可以要求删除任何字段的任何成员,并且如果您删除一个艺术家,您必须从其他 b 树中删除他的所有专辑和歌曲,请记住,例如,给定艺术家的所有歌曲不必在 b 树中彼此靠近对应歌曲。

我的问题是:有没有办法这样做(在删除作者后删除歌曲),而不必遍历其他 b 树的所有元素?我不是在寻找代码只是想法,因为我提出的所有想法都是蛮力的。

【问题讨论】:

  • 是的,这就是你应该做的。删除一首歌意味着从所有的树中删除。删除艺术家意味着删除他所有的歌曲。这里没有捷径。您不必在其他树中搜索,因为歌曲记录应该有指向所有树节点的指针。
  • 在您的问题中,您可能有字段和表格。如果你规范化你的模式,你最终会得到几个表。在设计程序时需要牢记这一点。

标签: database algorithm b-tree


【解决方案1】:

这是我的理解,可能并不完全正确。

通常在数据库实现中,B 树用于索引,因此除非您想强制用户为每一列建立索引,否则默认为每个字段创建 B 树是不必要的。虽然如此多的索引几乎在所有情况下都会导致快速读取(对所有内容都有索引,您不必进行全表扫描),但它也会导致插入/更新/删除非常慢,因为相应的数据有在每棵树中更新。我相信你知道,现代数据库至少有一个索引(主键),所以你将至少有一个 B 树,其中有一个主键的键,以及一个指向适当节点的指针。

B 树索引中的每个节点都应该有一个指向它所代表的完整对象的指针/引用。

创建的未来索引将包含您在索引中指定的属性,例如歌曲名称、艺术家等,但仍将包含指向相应节点的指针/引用。因此,当您修改歌曲标题时,您将需要修改所有索引引用的引用节点。如果您有任何将修改后的引用作为属性的索引,则必须修改该索引本身中的值。

不幸的是,我相信您的信念是正确的,即在删除/更新时您将不得不通过其他 B 树进行暴力破解,这是使用大量索引的缺点之一(更​​新/删除时间变慢) .如果您只是删除引用的节点,您最终可能会得到指向已删除对象的指针,这将(取决于您的语言)给您某种形式的 NullPointerException。为了防止这种情况,必须从所有树中删除它们的引用。

请记住,对索引进行全盘扫描仍然比全表扫描要好得多。

【讨论】:

  • btree 的扫描最终将取决于数据库模式和表之间的关系:如果正在修改的行包含索引字段,那么每个受影响的 btree 都必须更新。如果某个字段是另一个表中的外键(并且如果支持该功能),则必须执行一些一致性检查。
  • 你是对的,我说的是每棵树都必须更新,假设 B 树只是基于不同的主键进行索引,并且仍然包含索引中的所有属性(我相信这是提问者计划做的,但我可能错了)
  • 我明白,你的回答是正确的恕我直言。我只是想让他看到他可能不得不考虑问题的这个方面。谢谢!
  • 我的想法是为每个字段保留一个 BTree。每个 BTree 都有字段和歌曲行作为键,当我删除一个作者(例如)时,我必须找到他的所有歌曲并在所有剩余的 BTree 中删除它们。但我不知道这是否是最优的。删除是主要问题。有没有别的办法???我认为这很慢,但如果这是我唯一的选择。
猜你喜欢
  • 1970-01-01
  • 2013-03-16
  • 2012-01-13
  • 1970-01-01
  • 2011-02-09
  • 2012-11-05
  • 2016-10-10
  • 2014-09-20
  • 2012-07-25
相关资源
最近更新 更多