2008-11-01 142 views
87

我想构建一个查询,显示表中的所有结果,但是从表的起始位置偏移5。据我所知,MySQL的LIMIT需要一个限制和一个偏移量。有没有办法做到这一点?Mysql偏移量无限行

+1

这是一个完全有效的问题,但我想知道最好是抓住一切,并以编程方式忽略头几个记录。鉴于似乎是最好的答案(限制5,18446744073709551615)的恐怖,我非常喜欢解决MySQL的LIMIT的局限性。 – cesoid 2015-01-31 02:31:10

+2

@cesoid如果你想要`限制5000,18446744073709551615`,该怎么办?你不会为了你的代码看起来漂亮而获得额外的5000行。 – elipoultorak 2015-10-26 11:03:23

+0

@ user3576887我认为你是对的,我只是在考虑上面的问题,假设5是唯一的要求,而不是一些可能更大的变化量(而不是解决别人的问题)。 – cesoid 2015-10-28 14:29:52

回答

124

MySQL Manual on LIMIT

检索所有行从某个 偏移到最后的结果 集合中,可以使用一些大数目作为 的第二个参数。这种说法 检索的所有行第96列 到最后:

SELECT * FROM tbl LIMIT 95, 18446744073709551615; 
+83

太可怕了!我来到了这里,希望MySQL能够使Limit的条款成为可选的,但是也提供了偏移量......但不是! 我已经看到了这个18446744073709551615遍布整个代码,我在指责懒惰的程序员,但它是一个设计特征! – Petruza 2010-05-24 15:10:02

+7

awfull答案,但多数民众赞成在官方从MySQL文件。我可以说@ _ @ – GusDeCooL 2011-10-19 18:06:53

+16

18446744073709551615对于那些想知道的人来说是2^64-1。您可能需要小心,因为您无法将此值存储在32位整数中。您必须确保将其存储为字符串以确保兼容性。 – AlicanC 2011-12-07 22:51:51

17

至于你提到它限制是必需的,所以你需要使用的最大极限可能,这是18446744073709551615(最大无符号BIGINT的)

SELECT * FROM somewhere LIMIT 18446744073709551610 OFFSET 5 
+24

哇,这是MySQL团队的官方解决方案吗? – Antony 2011-05-23 18:11:16

3

另一种方法是选择一个autoimcremented列,然后使用具有过滤。

SET @a := 0; 
select @a:[email protected] + 1 AS counter, table.* FROM table 
HAVING counter > 4 

但是我可能会坚持使用高限制方法。

0

就在今天,我正在阅读有关从mysql表中获取大量数据(超过一百万行)的最佳方法。一种方法是,如所暗示的那样,使用LIMIT x,y,其中x是偏移量,而y是您想返回的最后一行。但是,正如我发现的那样,这不是最有效的方式。如果您有一个自动增量列,可以轻松使用SELECT声明和WHERE子句声明要从哪条记录开始。

例如, SELECT * FROM table_name WHERE id > x;

看来,当您使用LIMIT,MySQL的获取所有结果,然后只能说明你适合在记录偏移:没有最好的性能。

来源:对此问题的回答MySQL Forums。请注意,问题是大约6岁。

-1

我知道这是旧的,但我没有看到类似的回应,所以这是我将使用的解决方案。

首先,我会对表执行计数查询以查看存在多少记录。这个查询很快,通常执行时间可以忽略不计。喜欢的东西:

SELECT COUNT(*) FROM table_name; 

然后,我会用我的数了我的极限结果建立我的查询(因为这是行的最大数目表可能可能返回)。喜欢的东西:

SELECT * FROM table_name LIMIT count_result OFFSET desired_offset; 

或者可能是这样的:

SELECT * FROM table_name LIMIT desired_offset, count_result; 

当然,如果有必要,你可以从count_result减去desired_offset得到一个实际的,精确值提供为限。如果我真的可以确定提供的适当限制,传递“18446744073709551610”值就没有意义。

-5
WHERE .... AND id > <YOUROFFSET> 

ID可以是任何自动递增或唯一的数字列你有...

-1

使用这种其他question和合并与格雷格的答案那招,你可以使用〜0而不是最大的无符号BIGINT值:

SELECT * FROM tbl LIMIT ~0 OFFSET 95; 

SELECT * FROM tbl LIMIT 95, ~0; 
0

可以使用MYS QL声明与极限:

START TRANSACTION; 
SET @my_offset = 5; 
SET @rows = (SELECT COUNT(*) FROM my_table); 
PREPARE statement FROM 'SELECT * FROM my_table LIMIT ? OFFSET ?'; 
EXECUTE statement USING @rows, @my_offset; 
COMMIT; 

在MySQL 5.5.44测试。因此,我们可以避免插入数字18446744073709551615.

注意:事务可以确保变量@rows与执行语句时考虑的表格一致。

6

正如在其他答案中指出的那样,MySQL建议使用18446744073709551615作为限制中的记录数,但请考虑:如果您获得18,446,744,073,709,551,615条记录,您会做什么?事实上,如果你有10亿条记录,你会怎么做?

也许你确实想要超过10亿条记录,但我的观点是,你想要的数量有一些限制,它要小于18十亿分之一。为了稳定性,优化和可用性,我建议在查询中加入一些有意义的限制。这也可以减少任何人从未见过神奇数字的困惑,并且至少能够传达您愿意同时处理多少条记录的额外好处。

如果你真的必须从你的数据库中得到所有18条记录,也许你真正想要的是以1亿的增量抓取它们并循环1840亿次。