数据库设计 - “列表”存储

Fab*_*o20 1 database-design

我“即将”在我的一个应用程序上实现一项功能,该功能需要存储大量数据(播放列表)。

假设以下场景:

  • 一个用户可以有多个播放列表
  • 这些播放列表最多有 50 万个条目(可能更多)
  • 我必须能够获取、删除、重新排序或查询整个播放列表或使用索引
  • 目前每个用户都有一个播放列表;但
  • 我即将实现一项功能,允许用户拥有 1 个以上的播放列表。
  • 每个播放列表大约有 3500 个条目。有些可以高达 590k。

播放列表条目由以下类表示:

public class Item {
  private Long owner; // User
  private String data;
  private String name;
  private String author;
  private int index; // Index of this item on the list
}
Run Code Online (Sandbox Code Playgroud)

TL;DRList< Item >对于每个用户(每个用户超过 1 个),此列表可以扩展到 500k+ 个条目。

目前,我为此使用了基于 SQL 的存储,但是,它很慢,特别是当我需要移动索引时 - 慢到我的数据库驱动程序认为连接失败并泄漏的程度。

解释“移位索引”:假设我正在删除第 3 个索引 ( i = 3)处的一个项目,这意味着它之后的所有其他项目都需要向下移动一个索引,因此我稍后可以请求索引 3 并获取该项目以前是索引 4。

目前,我会在Order删除后减少所有元素的播放列表的列值。

当前播放列表项目表设计

Id (Ordering/Index) | PlayList (Id) | Owner (User) | Name | Author | Data
Run Code Online (Sandbox Code Playgroud)

哪种方法可以更好/更有效地存储这种“批量”数据,同时仍然能够查询和修改它?

我可以为此类数据更改/实施新的数据库软件,因为它非常大(我目前使用 Redis 和 MariaDB)。但是,我很想避免这样做。

Bas*_*que 5

用户有 >1 个播放列表

Vérace答案是正确的,只是它忽略了每个用户可能拥有多个播放列表的事实。

所以这是我的桌子设计图。我将一个列名更改为“sort_order”,因为在数据库和编程中名称“index”会引起各种混乱。

基本上,我怀疑您没有注意到“播放列表”中的“列表”,将每个人的收藏夹列表与可能选择的完整列表混为一谈。每个播放列表都是对所需项目(歌曲、书籍或任何您的问题 - 在问题中不清楚)的引用的集合。

在此处输入图片说明

表现

至于在现有行的排序顺序编号中插入新/更改的行时的性能问题,您可以显着降低此杂项的频率。

将您的排序顺序值增加一百、一千或一百万而不是一。您可以通过在现有行的编号之间分配一个排序顺序编号来插入新行,而无需进行任何移位。仅当 99 或 999 或 999,999 行碰巧已插入到递增行之间时,您才需要执行完整移位。在此之前,当出现带有中间数字的块时,您可能需要进行微调,但在行的小子集上,<100 或 <1,000 或 <1,000,000。

如果您需要向用户显示连续的 1、2、3……数字,请让数据库动态创建这些数字作为SELECT语句的一部分。