Mysql 具有数十亿条记录的多对多表是否会导致性能问题?
我正在构建一个包含3个表的数据库 用户表、ID、用户名 产品表,ID,产品名称 评级表,ID,用户ID,产品ID,评级 我的潜在用户将达到近1亿,产品将达到5000种。虽然不是每个用户都对每种产品进行评级,但我们仍然有理由假设我的评级表将有数十亿条记录。我对数据库的了解仅限于SQL查询,所以我想知道当我希望选择一个特定用户的所有评分时,它会变得非常慢吗 谢谢 更新:关于评级表,如果我将UserID和ProductID作为主键,保留ID列是否有必要或有任何好处?当谈到建模时,我一次只使用一个用户的评级,即选择属于user1的所有评级,在这些记录上执行操作,选择user2评级,在这些记录上执行操作,等等。在方便性和效率方面,有比多对多表更好的数据库结构吗 更新2:Mysql 具有数十亿条记录的多对多表是否会导致性能问题?,mysql,database,database-design,many-to-many,nosql,Mysql,Database,Database Design,Many To Many,Nosql,我正在构建一个包含3个表的数据库 用户表、ID、用户名 产品表,ID,产品名称 评级表,ID,用户ID,产品ID,评级 我的潜在用户将达到近1亿,产品将达到5000种。虽然不是每个用户都对每种产品进行评级,但我们仍然有理由假设我的评级表将有数十亿条记录。我对数据库的了解仅限于SQL查询,所以我想知道当我希望选择一个特定用户的所有评分时,它会变得非常慢吗 谢谢 更新:关于评级表,如果我将UserID和ProductID作为主键,保留ID列是否有必要或有任何好处?当谈到建模时,我一次只使用一个用户的
| time_spent | CREATE TABLE `time_spent` (
`product_id` mediumint(9) NOT NULL,
`user_id` bigint(20) unsigned NOT NULL,
`minutes_spent` int(10) unsigned NOT NULL,
PRIMARY KEY (`user_id`,`product_id`),
KEY `index_product_id` (`product_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci |
其中product_id为6位数,但将来可能会变长;用户id的长度为17位。上面描述的数据库模式可以使用。只要确保在UserID和ProductID上添加复合索引就可以了。关于性能,正如您所提到的,由于数十亿条记录,并且考虑到数据库的规模很大,所以有可能会受到小的影响。但你们对此无能为力,只要加强数据库机器 <>我不会考虑从评级表中删除ID。我知道它没有任何直接的作用。但我所看到的是ID表非常有用,当您最终编写复杂的查询和连接时,它会使事情变得更简单。去掉多:多表上的ID;您有一个“自然”主键用户ID ProductID。使用InnoDB,使评级与PK聚集在一起,从而“覆盖”。因此,您不需要Gordon建议的3列索引 你需要走另一条路吗?如果是这样的话,会显示INDEXProductID、UserID、Rating,这样您也可以通过这种方式获得“覆盖”索引 附录 如果您为一个用户选择最多5000行,并且您有PRIMARY KEYUserId、ProductID和InnoDB,那么所有这些行都将位于几十个块中。因此,即使有一个冷缓存,我们谈论的时间也不到一秒钟。如果您需要更新所有5000行,那么您正在触摸辅助键(如果它存在的话),这大约是5000次磁盘点击-这是一个很大的开销,尽管InnoDB的“更改缓冲区”以延迟的方式处理它
因此,如果你不需要从一个产品到另一个用户,比如查找一个产品的所有评级,那么就不要使用第二个索引。一点也不需要。您只需要ratingsUserId或更好的ratingsUserId、ProductId、Rating索引;我怀疑他们是否每个人都能利用if ID。而且ID是杂乱无章的,而且是开销。对于数十亿行来说,任何混乱都是昂贵的。因为这些是实时数据,我需要经常选择每个用户最多5000行,然后将这些行与最新数据进行比较,最后更新这些已更改的行。仅将产品id、用户id设置为主键就足够了吗?谢谢你。。。对于为一个用户查找大量行是有效的;产品标识。。。对于查找一个产品的多行非常有效。我将user\u id、product\u id设置为主键,product\u id设置为附加索引。唯一的问题是3列表非常疯狂地占用磁盘空间,请提供SHOW CREATE table;我想看看数据类型,等等。一个小的改进是使用比4字节INT小的东西来花费几分钟。看起来表及其索引每行大约需要100字节;这就是您看到的磁盘空间吗?