数据库
首页 > 数据库> > mysql-为“喜欢”之类的东西设计一个高度非规范化的表

mysql-为“喜欢”之类的东西设计一个高度非规范化的表

作者:互联网

我目前正在构建一个具有多种用户类型的Web应用程序,其中用户参与多种活动类型.

我需要设计一个表,将用户和活动之间的“喜欢”(赞,1等)关联起来.无论如何我都不是MySQL的专家,所以我想避免在我的数据库设计中走错路,尤其是使用这样的东西.

我在想的是一个如下表:

CREATE TABLE likes (
  from_id int(11) NOT NULL,
  from_type VARCHAR(100) NOT NULL,
  to_id int(11) NULL,
  to_type VARCHAR(100) NULL,
  posted TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY(from_id, from_type, to_id, to_type),
  INDEX(from_id, from_type),
  INDEX(to_id, to_type)
)Engine=InnoDB;

随着系统扩展,与此相关的性能问题是什么?这些“喜欢”将用于新闻提要中,因此会有很多读写操作.

有没有我根本没有想到的更好的方法?

提前致谢!

解决方法:

您的from_type和to_type字段(如VARCHAR(100))将浪费大量空间,并且与它们进行匹配将不如与对整数from_type_id和to_type_id进行匹配那样有效.当您向表中添加更多条目时,它们还将使维护索引的速度变慢.

如果您需要人类可读的类型名称,请制作另一个列出它们的表以及它们的数字ID.您可以使id成为该表的外键,尽管维护外键的完整性会带来一些成本.

大概不会有太多的类型,至少与表中的行数相比,因此需要它们的任何进程都可以只读取该表一次,而不是要求数据库在每次读取时进行联接.

关于索引:

这些将使您的插入速度变慢.您的目标应该是提供足够的服务所有读取查询,并使您确实拥有的查询尽可能多.

多列索引肯定是有用的,并且它们具有很好的属性,即所有前缀实际上也都已建立索引.也就是说,如果您在(a,b,c)上有一个索引,那么它也可以用作(a,b)上的索引,甚至可以用作在a上的索引. (MySQL将以这种方式使用索引).

这意味着,由于您有一个索引

(from_id, from_type, to_id, to_type)

那你仍然需要索引

(to_id, to_type)

但是你可以消除索引

(from_id, from_type)

使数据库分别维护该索引只会降低它的速度.

这也意味着您可能需要预先考虑一下索引中列的顺序.将类型放在id之前可能更有意义,因为您更有可能查询数据库中特定类型的所有喜欢,而不是特定ID(针对每种类型)的所有喜欢.

如果您按以下方式构建索引:

(to_type, to_id, from_type, from_id)
(from_type, from_id)

然后,您可以有效地搜索:

>全部喜欢源自某个类型(from_type)的所有对象
>全部喜欢源自特定对象(from_type,from_id)
>全部喜欢针对类型(to_type)的所有对象
>所有喜欢针对特定对象(to_type,to_id)
>(有趣的)所有人都喜欢针对特定对象的特定类型(例如,喜欢该特定“文章”的所有“人”)(to_type,to_id,from_type)
>最后,在所有四个(to_type,to_id,from_type,from_id)上都具有唯一性约束

标签:denormalization,mysql
来源: https://codeday.me/bug/20191101/1985647.html