我有超过40年的数十万个价格点。我想构建一个只返回3000个总数据点的查询,其中最后500个是最新的数据点,另一个2500只是其余数据的样本,均匀分布。
是否可以在一个查询中执行此操作?我如何只选择大量数据的样本?这是我仅仅获取其他2500个数据点样本的一个小例子:
1
2
3
4
5
6
7
8
9
10
我想要返回这样的内容:
1
5
10
这是最后500的查询:
SELECT * FROM price ORDER BY time_for DESC LIMIT 500
我不确定如何从其他数据点获取样本数据。
答案 0 :(得分:5)
试试这个:
(SELECT * FROM price ORDER BY time_for DESC LIMIT 500)
UNION ALL
(SELECT * FROM price WHERE time_for < (SELECT time_for FROM price ORDER BY time_for LIMIT 500, 1) ORDER BY rand() LIMIT 2500)
ORDER BY time_for
注意:它可能会很慢。这张桌子有多大?
仅从所有这些行获取主ID可能会更快,然后在缩小后将其连接到辅助查询中的原始ID。这是因为ORDER BY rand() LIMIT
必须对整个表进行排序。如果表很大,则可能需要很长时间,并且需要大量磁盘空间。仅检索ID会减少必要的磁盘空间。
答案 1 :(得分:3)
之前的答案很好,但您确实指定要将结果均匀分布,所以我也会添加这种可能性。通过在行上迭代计数器,您可以使用MOD运算符对均匀分布进行采样。我现在没有安装MYSQL来测试这个,所以如果语法不是100%现场,请道歉。但它应该足够接近,可能会给你一些想法。
( SELECT p1.*
FROM price p1
ORDER BY p1.time_for DESC
LIMIT 500 )
UNION ALL
( SELECT @i := @i + 1 AS row_num,
p2.*
FROM price p2,
(SELECT @i: = 0)
WHERE row_num > 500
AND (row_num % 500) = 0
ORDER BY time_for DESC )
第一个查询给出了500个最新行。第二个查询在此之后给出每第500行,从而从其余数据返回均匀分布。显然,您可以调整此参数以获得所需的样本间距。或者根据表格中的总行数来计算必要的间距,以准确给出2500条记录。