Three visitors on the first day, three on the second, two on the third. Eight people? Only if nobody returned. In our sample, several did: the three days contain five distinct visitor IDs.

We will calculate the exact answer first, then build daily sketches that can be combined later. The key idea is preserving enough information about overlap to estimate a union, instead of adding incompatible counts.

Explore the idea

Returning visitors do not become new people

Add another day and follow which IDs are actually new to the period.

6 ≠ 4

daily counts versus period distinct IDs

Six daily memberships belong to four IDs

Ben and Cy appear on both days. The union contains Ada, Ben, Cy, and Dee.

The events, including repeat visits

Names stand in for stable, fictional visitor IDs. We are counting distinct IDs, not proving how many individual humans visited. Identity changes and shared IDs are separate tracking problems.

events9 rows

Three days of repeat visitors

Names are fictional stable visitor IDs. There are nine events, eight daily memberships, and five distinct IDs.

iddayvisitor_id
12026-01-01Ada
22026-01-01Ben
32026-01-01Cy
42026-01-01Ada
52026-01-02Ben
62026-01-02Cy
72026-01-02Dee
82026-01-03Ada
92026-01-03Eli

Ada appears twice on the first day. A distinct count within that day handles the repeated event correctly:

Count distinct IDs within each day

SELECT day::VARCHAR AS day, count(DISTINCT visitor_id) AS unique_visitors
FROM events GROUP BY day ORDER BY day;
Expected result · sample data3 rows
day unique_visitors
2026-01-01 3
2026-01-02 3
2026-01-03 2

But the daily counts have discarded which IDs overlapped. Ben and Cy appear on both January 1 and 2; Ada returns on January 3.

Establish the exact answer

Compare the sum of daily counts with an exact distinct count over the entire period:

Compare adding counts with counting the union

WITH daily AS (SELECT day, count(DISTINCT visitor_id) AS n FROM events GROUP BY day)
SELECT (SELECT sum(n) FROM daily) AS sum_of_daily_counts,
       (SELECT count(DISTINCT visitor_id) FROM events) AS period_unique_visitors;
Expected result · sample data1 row
sum_of_daily_counts period_unique_visitors
8 5

Eight daily memberships belong to five distinct IDs. SUM is appropriate for additive measures such as event counts. A distinct count is not additive across overlapping groups.

If your raw data is available and an exact COUNT(DISTINCT visitor_id) meets your needs, use it. This tiny example does not need approximation. It exists to make the overlap visible before we introduce a technique for storing compact, mergeable summaries.

Store a daily sketch, then merge it

Query.Farm’s DataSketches extension can build an HLL sketch from IDs and estimate the distinct count represented by it. The setup creates daily_sketches with one datasketch_hll(12, visitor_id) value per day. The 12 controls sketch size and accuracy; it is not a requested number of visitors.

Merge those saved sketches, then ask for an estimate:

Estimate the union from saved daily sketches

SELECT round(datasketch_hll_estimate(
  datasketch_hll_union(12, sketch)
), 2) AS estimated_visitors
FROM daily_sketches;
Expected result · sample data1 row
estimated_visitors
5

The merge operates on sketch state, not on the displayed daily estimates. An estimate alone has lost the information needed for a union. That is the useful distinction between saving a count and saving a mergeable sketch.

Our result rounds to 5.00, matching the exact answer. That agreement on five IDs is not an accuracy guarantee. Sketches are approximate; larger inputs can produce estimates above or below the exact count. Rounding improves presentation, not accuracy.

Keep the sketch family, ID representation, and configuration consistent across partitions. Test the chosen settings against exact counts on representative samples before deciding the error is acceptable.

Choose a smaller reporting window

Because each daily sketch is stored separately, we can select the days we need and combine only those summaries. The first two days contain four distinct IDs even though their daily counts sum to six.

Your turn · check your answer

Combine just the first two days

Return estimated_visitors for January 1–2 using the stored daily sketches. Round the estimate to two decimal places.

See the expected result
Your target result1 row
estimated_visitors
4
Sample data is loaded for you.

Preparing the editor…

Need a hint?

Filter the daily sketch rows before merging them. Adding daily counts counts Ben and Cy twice.

Show a solution
SELECT round(datasketch_hll_estimate(
  datasketch_hll_union(12, sketch)
), 2) AS estimated_visitors
FROM daily_sketches
WHERE day <= DATE '2026-01-02';

For a real week, define its date boundary and time zone before assigning events to days. These fixtures already contain dates, so no time-zone conversion is hidden inside the example.

What this technique saves—and what it does not

Building a sketch still requires reading its input records. The reuse happens afterward: a rolling-period estimate can read the saved daily summaries instead of all the original events. Measure that tradeoff on the size and update pattern you actually have.

Ordinary HLL union does not provide subtraction. If an older partition is corrected, rebuild or replace that partition’s sketch and recompute the requested union; do not subtract its previous estimate from a total. Preserve raw data according to the accuracy and correction requirements of your system.

Use exact aggregates when the result must be exact, including reconciliation of charges. Use mergeable sketches when compact reusable summaries and an understood approximation fit the question. For another common source of inflated metrics, try fixing totals after a join.