Mysql 根据用户拆分数据库';身份证

Mysql 根据用户拆分数据库';身份证,mysql,query-optimization,Mysql,Query Optimization,我有一个500万行的数据库,它不断增长,使用它进行操作变得越来越困难 将表拆分为10个表(v0\u表、v1\u表……v9\u表)是一个好主意,其中数字(v*)是用户id的第一个数字 在我的例子中,用户id不是自动递增的,因此它将在这10个表中对数据进行均匀排序 问题是我从来没有做过类似的事情 有人能看出缺点吗 编辑: 如果您能帮助我调整结构或查询,我将不胜感激。 因此,最慢的查询是以下查询: SELECT logos.user, logos.date, logos

我有一个500万行的数据库,它不断增长,使用它进行操作变得越来越困难

将表拆分为10个表(v0\u表、v1\u表……v9\u表)是一个好主意,其中数字(v*)是用户id的第一个数字

在我的例子中,用户id不是自动递增的,因此它将在这10个表中对数据进行均匀排序

问题是我从来没有做过类似的事情

有人能看出缺点吗

编辑:

如果您能帮助我调整结构或查询,我将不胜感激。 因此,最慢的查询是以下查询:

SELECT logos.user, 
       logos.date, 
       logos.level, 
       logos.title, 
       Count(guesses.id), 
       Sum(guesses.points) 
FROM   logos 
       LEFT JOIN guesses 
              ON guesses.user = '".$user['uid']."' 
                 AND guesses.done = '1' 
                 AND guesses.logo = logos.id 
WHERE  open = '1' 
GROUP  BY level 
其中猜测表:

+--------+------------+------+-----+-------------------+----------------+
| Field  | Type       | Null | Key | Default           | Extra          |
+--------+------------+------+-----+-------------------+----------------+
| id     | int(11)    | NO   | PRI | NULL              | auto_increment |
| logo   | int(11)    | NO   | MUL | NULL              |                |
| user   | int(11)    | NO   | MUL | NULL              |                |
| date   | timestamp  | NO   |     | CURRENT_TIMESTAMP |                |
| points | int(4)     | YES  | MUL | 100               |                |
| done   | tinyint(1) | NO   | MUL | 0                 |                |
+--------+------------+------+-----+-------------------+----------------+
标识表:

+-------+--------------+------+-----+-------------------+----------------+
| Field | Type         | Null | Key | Default           | Extra          |
+-------+--------------+------+-----+-------------------+----------------+
| id    | int(11)      | NO   | PRI | NULL              | auto_increment |
| name  | varchar(100) | NO   |     | NULL              |                |
| img   | varchar(222) | NO   | MUL | NULL              |                |
| level | int(3)       | NO   | MUL | NULL              |                |
| date  | timestamp    | NO   | MUL | CURRENT_TIMESTAMP |                |
| user  | int(11)      | NO   | MUL | NULL              |                |
| open  | tinyint(1)   | NO   | MUL | 0                 |                |
+-------+--------------+------+-----+-------------------+----------------+
说明:

+----+-------------+---------+------+----------------+------+---------+-------+------+----------------------------------------------+
| id | select_type | table   | type | possible_keys  | key  | key_len | ref   | rows | Extra                                        |
+----+-------------+---------+------+----------------+------+---------+-------+------+----------------------------------------------+
|  1 | SIMPLE      | logos   | ref  | open           | open | 1       | const |  521 | Using where; Using temporary; Using filesort |
|  1 | SIMPLE      | guesses | ref  | done,user,logo | user | 4       | const |   87 |                                              |
+----+-------------+---------+------+----------------+------+---------+-------+------+----------------------------------------------+

简短而甜蜜:不,这从来不是个好主意。您的表是否正确索引?MySQL是否正确调整?您的查询是否高效?您正在使用缓存吗?

您可能希望检查数据库中的其他表,看看它们是否可以拆分为其他数据库,而不是对表进行切分。例如,从未连接到的表就是这种垂直分区的最佳候选表


这允许您为较小的数据集优化硬件。

您的问题不是数据太多,而是这些数据没有正确索引。尝试添加索引:

CREATE INDEX open_level ON logos(open, level)
这应该避免使用临时的;在徽标上使用文件排序


基本上,这个查询需要在这个表上建立一个索引来覆盖两件事:open-for
其中open='1'
和level-for
按级别分组,因为MySQL将首先按open进行筛选,然后按级别对结果进行分组(在处理过程中隐式地按其排序).

这似乎会让查询变得非常混乱。在我可以使用的地方使用memcache,也增加了mysql缓存,索引了表(如果正确的话不知道)。问题是有500个用户在线,而且该表经常更新。。。为什么这不是一个好主意?以不同的方式拆分表可能有意义,但不是您在OP中建议的方式。许多数据库将“频繁更新”字段与已完成的“几乎从未更新”字段分开放在一个表中。我只是在寻求额外的改进。即使现在只有我在线时,也需要0.3秒才能获得30个条目(从5.2百万开始)。但是当500个用户在线时,它会变得疯狂。在我看来,这些表的索引不正确。您是否设置并检查了mysql慢速查询日志?设置好,然后对这些语句进行“解释”,看看它们是否使用索引,然后进行相应的调整。除此之外,如果看不到具体的表结构,将很难提供帮助。在我看来,不这样做的原因列表相当长,但基本上可以归结为维护和数据完整性。我在表的结构上添加了更多细节。我将非常感谢您的帮助。这里的问题是我有3个表,其中2个经常使用。所以第三个是独立的,通常是memcached。你能告诉我为什么分裂是个坏主意吗?理论上,分裂不是个坏主意。您可以并行化查询,使用更小的索引,等等。实际上,MySQL并不是很适合这样做。根据我的经验,拆分表并独立地调优每一组表更容易。MySQL确实支持分区功能,但我不确定它在实践中的效果如何。你能解释一下它是做什么的,为什么它只包含“开放”和“级别”吗?老实说,这个索引很有用。将CPU负载降低20%。谢谢:)虽然OP有所不同,但您帮助了优化的最终请求。