Google cloud platform 如何实现分页?
我有一个Google cloud platform 如何实现分页?,google-cloud-platform,google-cloud-spanner,Google Cloud Platform,Google Cloud Spanner,我有一个People表(Id,first\u name,last\u name),其中主键是Id。我希望能够查找表中按排序的前N个人(姓、名、Id)。在某些情况下,我需要查找接下来的N个人,以此类推。我想有效地做到这一点。最好的方法是什么?有两种主要方法: 使用限制和偏移 使用限制和上一页的键 偏移策略允许您读取任意页面,但效率不高,因为每次运行查询时,它都必须读取以前所有页面中的行。这是最容易实现的策略,也是可以接受的策略(特别是如果您只需要前几页),但通常不建议使用。“上一页”策略的关键
People
表(Id,first\u name,last\u name)
,其中主键是Id
。我希望能够查找表中按排序的前N个人(姓、名、Id)
。在某些情况下,我需要查找接下来的N个人,以此类推。我想有效地做到这一点。最好的方法是什么?有两种主要方法:
- 使用
和限制
偏移
- 使用
和上一页的键限制
(LastName,FirstName,Id)
排序的表中获取结果:
您可能希望确保所有查询都查看数据库数据的一致快照,因此您希望确保查询序列始终从相同的时间戳读取。最简单的方法是将第一个查询设置为只读事务,并将returnReadTimestamp
设置为true。然后,后续查询也可以是只读事务,它们应该使用原始查询返回的时间戳作为其readTimestamp。请注意,无论您选择何种方法,orderby
子句对于确保查询序列中的结果一致性至关重要。
假设返回的最后一行是(1709,“John”,“Smith”)
。然后,第一次尝试查询以获取下一页结果可能如下所示:
SELECT
t.id,
t.first_name,
t.last_name
FROM
People as t
WHERE
t.last_name > "Smith"
OR
(t.last_name = "Smith" and t.first_name > "John")
OR
(t.last_name = "Smith" and t.first_name = "John" AND t.id > 1709)
ORDER BY
t.last_name,
t.first_name,
t.id
LIMIT
@limit_rows
中间的
WHERE
子句是新的。但是写这个谓词比你想象的要复杂。您可能必须处理空值。您必须处理多个名为John Smith的人具有不同id
值的情况。您需要非常小心使用浮点数和NaN
值。Cloud Panner的Read API在这种情况下也很有用,因为它使在表上对范围扫描进行分页变得更容易。Hi Mike,感谢您发布这篇文章。如果您正在使用快照并提供时间戳,那么为什么需要添加所有这些where约束呢。你就不能说t.id>1709吗?或者,您是在试图说明快照由于垃圾收集而过期的情况吗?垃圾收集与此无关。额外约束的原因是,问题说我们希望按(Lastname、Firstname、Id)的顺序返回查询结果,这与主键顺序不同。注意,可能有一个t.id小于1709的结果仍然是需要的结果(例如“Wilkes”、“Bob”805)
SELECT
t.id,
t.first_name,
t.last_name
FROM
People as t
WHERE
t.last_name > "Smith"
OR
(t.last_name = "Smith" and t.first_name > "John")
OR
(t.last_name = "Smith" and t.first_name = "John" AND t.id > 1709)
ORDER BY
t.last_name,
t.first_name,
t.id
LIMIT
@limit_rows