32

我正在编写一个非常非常简单的查询,它只是根据其唯一 ID 从集合中获取文档。经过一番挫折(我是 mongo 和 async / await 编程模型的新手),我想通了:

IMongoCollection<TModel> collection = // ...
FindOptions<TModel> options = new FindOptions<TModel> { Limit = 1 };
IAsyncCursor<TModel> task = await collection.FindAsync(x => x.Id.Equals(id), options);
List<TModel> list = await task.ToListAsync();
TModel result = list.FirstOrDefault();
return result;

有效,太好了!但我不断看到对“查找”方法的引用,我解决了这个问题:

IMongoCollection<TModel> collection = // ...
IFindFluent<TModel, TModel> findFluent = collection.Find(x => x.Id == id);
findFluent = findFluent.Limit(1);
TModel result = await findFluent.FirstOrDefaultAsync();
return result;

事实证明,这也很有效,太棒了!

我敢肯定,我们有两种不同的方法来实现这些结果是有重要原因的。这些方法之间有什么区别,为什么我应该选择其中一种?

4

2 回答 2

44

区别在于语法。 Find并且FindAsync两者都允许构建具有相同性能的异步查询,仅

FindAsync返回不会一次加载所有文档的游标,并为您提供从数据库游标中一一检索文档的界面。这在查询结果很大的情况下很有帮助。

Find通过它内部从光标检索文档并立即返回所有文档的方法为您提供更简单的语法ToListAsync

于 2015-06-05T01:11:32.320 回答
0

想象一下,您在 Web 请求中执行此代码,通过调用 find 方法,请求的线程将被冻结,直到数据库返回结果它是一个同步调用,如果它是一个需要几秒钟才能完成的长数据库操作,您将有一个可用于服务 Web 请求的线程什么都不做,只是等待数据库返回结果,并浪费宝贵的资源(线程池中的线程数是有限的)。

使用 FindAsync,您的 Web 请求线程将在等待数据库返回结果时空闲,这意味着在数据库调用期间,该线程可以空闲参与另一个 Web 请求。当数据库返回结果时,代码继续执行。

对于从文件系统读取/写入、数据库操作、与其他服务通信等长操作,使用异步调用是一个好主意。因为在您等待结果时,线程可用于服务另一个 Web 请求。这更具可扩展性。

看看这篇微软文章https://msdn.microsoft.com/en-us/magazine/dn802603.aspx

于 2015-06-04T18:07:16.530 回答