当前位置: 首页 > 面试题库 >

如何使用分页将分页应用于SQL查询的结果?

滕学义
2023-03-14
问题内容

我有连接3个表的SQL查询,一个表只是将其他两个表连接起来的多对多表。我使用Spring JDBCResultSetExtractor将ResultSet转换成我的Objects,看起来像这样:

class Customer {
    private String id;
    private Set<AccountType> accountTypes;
    ...
}

ResultSetExtractor实现如下所示:

public List<Client> extractData(ResultSet rs) throws SQLException,
    DataAccessException {
        Map<Integer, Client> clientsMap = new LinkedHashMap<Integer, Client>();
        while (rs.next()) {
            int id = rs.getInt("id");
            // add the client to the map only the first time
            if (!clientsMap.containsKey(id)) {
                Client client = new Client();
                client.setId(id);
                ...
                clientsMap.put(id, client);
            }
            // always add the account type to the existing client
            Client client = clientsMap.get(id);
            client.addAccountType(extractAccountTypeFrom(rs, id));
        }
        return new ArrayList<Client>(clientsMap.values());
}

无需分页即可正常工作。

但是,我需要对这些结果进行分页。我通常的做法是将其添加到查询中,例如:

SELECT ... ORDER BY name ASC LIMIT 10 OFFSET 30;

但是,由于此查询具有联接,因此当我限制结果数量时,实际上是在限制JOINED结果的数量(即,由于客户端出现的次数与其所拥有的帐户类型的数量一样多,因此不应用LIMIT客户数量,但是客户数量*
accountTypes,这不是我想要的数量)。

我想出的唯一解决方案是从查询中删除LIMIT(以及OFFSET,因为那也将是错误的),并以编程方式应用它们:

List<Client> allClients = jdbcTemplate.query....
List<Client> result = allClients.subList(offset, offset+limit);

但这显然不是一个很好的,有效的解决方案。有没有更好的办法?


问题答案:

编写问题如何使您思考是很有趣的,并且对于想出自己的问题的解决方案实际上有很大帮助。

通过将查询的分页部分添加到我的主查询的子查询中,而不是添加到主查询本身,就可以解决此问题。

例如,不要这样做:

SELECT client.id, client.name ...
FROM clients AS client
LEFT JOIN client_account_types AS cat ON client.id = cat.client_id
FULL JOIN account_types AS at ON cat.account_type_id = at.id
ORDER BY client.name ASC
LIMIT 10 OFFSET 30;

我正在这样做:

SELECT client.id, client.name ...
FROM (
    SELECT * FROM clients
    ORDER BY name ASC
    LIMIT 10 OFFSET 0
) AS client
LEFT JOIN client_account_types AS cat ON client.id = cat.client_id
FULL JOIN account_types AS at ON cat.account_type_id = at.id;

希望这对其他人也有帮助。



 类似资料:
  • 本文向大家介绍SQL Server 分页查询通用存储过程(只做分页查询用),包括了SQL Server 分页查询通用存储过程(只做分页查询用)的使用技巧和注意事项,需要的朋友参考一下 自开始做项目以来,一直在用。这段存储过程的的原创者(SORRY,忘记名字了),写得这段SQL代码很不错,我在这个基础上,按照我的习惯以及思维方式,调整了代码,只做分页查询用。 调用方法: prcPageResult

  • 我有两种型号: 用户 用户有很多帖子。帖子有很多评论,评论属于帖子。这很简单。 现在我想加载所有的帖子的认证用户与它的评论,如果帖子有评论今天创建。如果帖子今天没有评论,它将不会被加载。这些帖子也将被分页。如何建立查询在laravel雄辩? 我试过这样的方法:

  • 问题内容: 我正在尝试按日期对我的讨论区中的帖子进行排序。这是我的代码: 这在语法上有什么问题吗?如果没有,还有什么可能是错误的?基本上发生的是结果没有显示出来。我删除了Order,它可以工作(但当然没有排序…) 问题答案: 订购应超出限制:

  • 本文向大家介绍如何用java实现分页查询,包括了如何用java实现分页查询的使用技巧和注意事项,需要的朋友参考一下 1.基本思路 我现阶段的分页查询的实现是基于sql语句的。 构造出相应的a和b就可以查询出想要的数据,在显示在页面上。重点是要构造出当前的页数,就要封装一个javaBean,存储有关分页的基本属性。 这样只需在service层计算想要的页数,并封装基本的信息,在查询出来显示在前端就可

  • 使用数据库的应用程序,多数情况下都需要使用 “分页” 这个功能。尤其是在 Web 应用程序中,后端的分页查询尤其的普遍。 在以往的使用经验中,一个分页查询,除了能获取到一个列表外,我们通常需要如下几个信息才能在客户端显示出一个完整的翻页条。 当前页数 -- 第几页 页大小 -- 每页有多少条记录 总页数 -- 一共多少页 总记录数 -- 如果不分页,一共有多少条记录 当我们获得了这四条信息后,对于

  • limt 分页查询 查询前3条记录 分页公式: (offset - 1) * limit SELECT name FROM `student` LIMIT 0, 3; Student.findAll( { attributes:['name'], // 当前页 offset:0, // 每页显示的条数 limit:3 }) 分页案例 router.ge