我在本地电脑上建立了一个mysql表来存储股市数据。表名为minute_data
,结构很简单:
您可以看到我将键列设为日期和符号的组合 -> concat(date,symbol)
。通过这种方式,我执行了一个 insert ignore ...
查询以将数据添加到表中,而无需复制日期/符号组合。
有了这张表,数据检索就很简单了。假设我想获取符号 CSCO
的所有数据,那么我可以简单地执行以下查询:
select * from minute_data where symbol = "CSCO" order by date;
一切都在“工作”。该表现在包含来自 1000 多个品种的数据,已经超过 2200 万行。我认为所有 1000 个符号还没有填满一半,所以我希望继续增加表格的大小。
查询此表时,我开始发现严重的性能问题。例如,下面的查询(我经常想这样做,查看特定交易品种的最新日期)需要 1 分钟多才能完成,并且只返回 1 行!
select * from minute_data where symbol = "CSCO" order by date desc limit 1;
这个查询(也很重要)平均也需要 1 分钟多的时间:
select count(*), symbol from minute_data group by symbol;
性能问题使得继续以这种方式处理数据变得不现实。这些是我想问社区的问题:
继续将我的数据集构建到这张表中是否徒劳无功?
对于这样的数据集,MySQL 是一个糟糕的选择吗?
我可以对该表做些什么来提高性能?
为此我应该使用哪种数据结构(而不是 MySQL 表)?
谢谢!
更新
我正在提供 explain
的输出,对于以下 2 个查询也是如此:
explain select count(*), symbol from minute_data group by symbol;
explain select * from minute_data where symbol = "CSCO" order by date desc limit 1;
更新 2
非常简单的修复。我执行此查询以删除上面定义的无用 key_col
,并在 2 列上创建了主键:日期和符号:
alter table minute_data drop primary key, add primary key (date,symbol);
现在我尝试了以下查询,并在不到 1 秒内完成:
select * from minute_data where symbol = "CSCO" order by date desc limit 1;
此查询仍需要很长时间才能完成(72 秒)。我想这仍然是因为查询必须在一个查询中列出所有 2200 万行?:
select count(*), symbol from minute_data group by symbol;
最佳答案
你的 key_col 完全没用。您知道可以在多列上使用主键吗?我建议您删除该列并按此顺序在 (date, symbol) 上创建一个新的主键,因为您的日期列具有更高的基数。此外,您还可以(如果需要的话)在(符号,日期)上创建另一个唯一索引。发布您最重要的查询的EXPLAIN
。 symbol
的基数是多少?
更新:
您在解释中可以看到,没有可以使用的索引,它扫描了整个 2250 万行。请尝试上面提到的。如果您现在不想删除 key_col,您至少应该在符号列上添加一个索引。
关于mysql - 我的大型 mysql 表注定要失败吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15612361/