如何在Firestore中高效聚合和计算平均值?

huangapple go评论61阅读模式
英文:

How to aggregate and calculate averages efficiently in Firestore?

问题

我在Firestore中设置了多个集合。特别是,我有一个grades集合,其中每个问题都有一个文档。

我的目标是聚合这些成绩并计算每个模块的平均分。我了解到Firestore作为NoSQL数据库,不原生支持服务器端计算或复杂的聚合查询。

到目前为止,我考虑了两种方法:

在客户端读取所有文档:我可以在客户端获取所有相关文档并在客户端计算平均值。然而,随着文档数量的增加,这似乎可能变得昂贵。

使用Cloud Functions计算平均值:这将涉及触发Cloud Function以在添加新成绩时更新平均值。然而,这似乎也可能显著增加写操作的数量。

有没有任何想法,不会导致疯狂的读取或写入量?

英文:

I have Firestore set up with several collections. Notably, I have a grades collection, with a document for each question.

My goal is to aggregate these grades and calculate the average for each module. I understand that Firestore, being a NoSQL database, doesn't natively support server-side computations or complex aggregation queries.

So far, I've considered two approaches:

Reading all documents on the client side: I could fetch all relevant documents and calculate the average on the client side. However, this seems like it could become expensive as the number of documents grows.

Using Cloud Functions to calculate averages: This would involve triggering a Cloud Function to update an average whenever a new grade is added. However, this also seems like it could increase the number of write operations significantly.

Does anyone have any idea that wouldn't result in a crazy amount of reads or writes?

答案1

得分: 1

> 在客户端读取所有文档:我可以在客户端获取所有相关文档并计算平均值。但是,随着文档数量的增加,这似乎可能变得昂贵。

在客户端读取所有文档并不是一个选项,因为在集合中的文档数量达到一定程度时,这可能会变得昂贵。这可能仅适用于小型数据集。

> 使用云函数来计算平均值:这将涉及触发云函数以在添加新成绩时更新平均值。

这将是在每次添加新成绩时计算平均值的一个选项。这个选项应该与count()函数一起使用。此外,请注意,在计算集合中的文档数量或由Firestore查询返回的文档时,存在一些限制。但是,在涉及定价时,请注意:

> 对于像count()这样的聚合查询,每批最多匹配查询的1000个索引条目都会收取一次文档读取费用。对于匹配0个索引条目的聚合查询,至少收取一次文档读取费用。

因此,计算文档可以被认为是一个非常便宜的操作。

> 不过,这似乎也可能会显著增加写操作的数量。

由于每次添加新成绩时都会写入新的平均值,是的,写操作的数量会增加,但另一方面,您将显著减少读操作的数量,这将使整体成本更便宜。

英文:

> Reading all documents on the client side: I could fetch all relevant documents and calculate the average on the client side. However, this seems like it could become expensive as the number of documents grows.

Reading all documents client-side isn't an option, as it can become costly when you reach a large number of documents in the collection. It might work only for small data sets.

> Using Cloud Functions to calculate averages: This would involve triggering a Cloud Function to update an average whenever a new grade is added.

That would be an option to calculate the average each time a new grade is added. This option should work hand in hand with the count() function. Also note, there are some limitations when it comes to counting the documents in a collection or the document that are returned by a Firestore query. However, when it comes to pricing, please note that:

> For aggregation queries such as count(), you are charged one document read for each batch of up to 1000 index entries matched by the query. For aggregation queries that match 0 index entries, there is a minimum charge of one document read.

So counting documents can be considered a really cheap operation.

> However, this also seems like it could increase the number of write operations significantly.

Since you write the new average each time a new grade is added, yes, the number of writes will increase, but on the other hand, you'll significantly decrease the number of reads, which will make it cheaper overall.

huangapple
  • 本文由 发表于 2023年5月10日 14:49:35
  • 转载请务必保留本文链接:https://go.coder-hub.com/76215618.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定