在C#项目中使用MongoDB存储数据时,当需要展示列表类数据,比如商品列表、用户列表等场景,通常需要对查询结果进行分页处理,避免一次性加载过多数据导致性能问题。MongoDB Driver提供了Skip和Limit方法,可以很方便地实现分页查询功能。

环境准备
首先需要在项目中安装MongoDB Driver的NuGet包,目前主流版本是2.x系列,安装命令如下:
dotnet add package MongoDB.Driver
安装完成后,需要先建立MongoDB的连接,获取对应的数据库和集合对象,示例代码如下:
using MongoDB.Driver;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
// 定义数据实体类
public class User
{
public string Id { get; set; }
public string UserName { get; set; }
public int Age { get; set; }
public DateTime CreateTime { get; set; }
}
class Program
{
static async Task Main(string[] args)
{
// MongoDB连接字符串,本地默认地址
string connectionString = "mongodb://127.0.0.1:27017";
// 创建客户端
var client = new MongoClient(connectionString);
// 获取数据库,数据库名为test_db
var database = client.GetDatabase("test_db");
// 获取集合,集合名为users
var userCollection = database.GetCollection<User>("users");
}
}
Skip和Limit分页核心逻辑
MongoDB的Skip方法用于跳过指定数量的前置文档,Limit方法用于限制返回的文档数量,两者结合就能实现分页效果。分页的核心计算公式如下:
- Skip数量 = (当前页码 - 1) * 每页条数
- Limit数量 = 每页条数
需要注意页码通常从1开始计数,避免出现负数Skip的情况。
完整分页查询实现
下面是一个完整的分页查询示例,包含参数校验、查询、返回总条数和分页数据:
/// <summary>
/// 分页查询用户列表
/// </summary>
/// <param name="collection">用户集合</param>
/// <param name="pageIndex">当前页码,从1开始</param>
/// <param name="pageSize">每页条数</param>
/// <returns>总条数和当前页数据</returns>
static async Task<(long totalCount, List<User> data)> GetUserPageAsync(IMongoCollection<User> collection, int pageIndex, int pageSize)
{
// 参数校验
if (pageIndex < 1) pageIndex = 1;
if (pageSize < 1) pageSize = 10;
// 计算需要跳过的文档数量
int skipCount = (pageIndex - 1) * pageSize;
// 获取总文档数量,这里可以根据需要添加过滤条件
long totalCount = await collection.CountDocumentsAsync(Builders<User>.Filter.Empty);
// 执行分页查询,先Skip再Limit,可添加排序保证分页顺序稳定
var data = await collection
.Find(Builders<User>.Filter.Empty)
.Sort(Builders<User>.Sort.Descending(u => u.CreateTime)) // 按创建时间倒序
.Skip(skipCount)
.Limit(pageSize)
.ToListAsync();
return (totalCount, data);
}
调用上述方法的示例:
static async Task TestPageQuery()
{
string connectionString = "mongodb://127.0.0.1:27017";
var client = new MongoClient(connectionString);
var database = client.GetDatabase("test_db");
var userCollection = database.GetCollection<User>("users");
// 查询第2页,每页10条数据
var (total, list) = await GetUserPageAsync(userCollection, 2, 10);
Console.WriteLine($"总条数:{total},当前页数据条数:{list.Count}");
foreach (var user in list)
{
Console.WriteLine($"用户ID:{user.Id},用户名:{user.UserName},年龄:{user.Age}");
}
}
注意事项
使用Skip和Limit分页时,需要注意以下几点:
- 当数据量非常大时,Skip的偏移量过大会导致查询性能下降,因为MongoDB需要扫描跳过的前置文档。如果数据量超过百万级,建议结合索引和范围查询优化分页逻辑。
- 分页查询时最好添加排序条件,否则MongoDB返回的数据顺序可能不稳定,导致分页出现重复或遗漏数据。
- 如果查询有过滤条件,CountDocumentsAsync和Find方法需要添加相同的过滤条件,保证总条数和分页数据匹配。
如果需要在分页时同时获取总页数,可以用总条数除以每页条数,有余数的话总页数加1,公式为:总页数 = (int)Math.Ceiling((double)totalCount / pageSize)。
C#MongoDB_DriverSkip_Limit分页查询修改时间:2026-07-21 05:36:23