Skip to content

Commit 0dda4ab

Browse files
committed
Add Get A Quick Approximate Count Of A Large Table as a Rails TIL
1 parent 6bc8897 commit 0dda4ab

File tree

2 files changed

+40
-1
lines changed

2 files changed

+40
-1
lines changed

README.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ pairing with smart people at Hashrocket.
1010

1111
For a steady stream of TILs, [sign up for my newsletter](https://crafty-builder-6996.ck.page/e169c61186).
1212

13-
_1285 TILs and counting..._
13+
_1286 TILs and counting..._
1414

1515
---
1616

@@ -797,6 +797,7 @@ _1285 TILs and counting..._
797797
- [Find Records With Multiple Associated Records](rails/find-records-with-multiple-associated-records.md)
798798
- [Force All Users To Sign Out](rails/force-all-users-to-sign-out.md)
799799
- [Generating And Executing SQL](rails/generating-and-executing-sql.md)
800+
- [Get A Quick Approximate Count Of A Large Table](rails/get-a-quick-approximate-count-of-a-large-table.md)
800801
- [Get ActiveRecord Attribute Directly From Database](rails/get-active-record-attribute-directly-from-database.md)
801802
- [Get An Array Of Values From The Database](rails/get-an-array-of-values-from-the-database.md)
802803
- [Get An Empty ActiveRecord Relation](rails/get-an-empty-activerecord-relation.md)
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
# Get A Quick Approximate Count Of A Large Table
2+
3+
Let's say our Rails app has a massive `events` table in it's Postgres database.
4+
We might be tempted to reach for an ActiveRecord API method like `Event.count`
5+
to get the number of records in the table. For tables with millions of rows,
6+
this is going to be slow.
7+
8+
If all we need is an approximate count, there is a faster way that uses some of
9+
PostgreSQL's internal bookkeeping.
10+
11+
We can request the approximate number of tuples recorded for our table by name.
12+
This query can be processed as raw SQL by the `#execute` method available on
13+
`ActiveRecord::Base.connection`.
14+
15+
```ruby
16+
ActiveRecord::Base.connection.execute(<<~SQL)
17+
select reltuples::numeric as count
18+
from pg_class
19+
where relname='events';
20+
SQL
21+
```
22+
23+
That is going to spit out the `PG::Result` object which doesn't look like much
24+
on its own.
25+
26+
```
27+
#<PG::Result:0x00 ...>
28+
```
29+
30+
If we tack on a couple other methods, we can get the count as our result.
31+
32+
```ruby
33+
ActiveRecord::Base.connection.execute(<<~SQL).to_a.first["count"].to_i
34+
select reltuples::numeric as count
35+
from pg_class
36+
where relname='events';
37+
SQL
38+
```

0 commit comments

Comments
 (0)