Cardinality Aggregation: Näherungswerte richtig einordnen
AI generated
_doc
_index
Elasticsearch · OpenSearch · Cardinality Aggregation · HyperLogLog
Cardinality Aggregation
Näherungswerte richtig einordnen

Eine exakte Zählung eindeutiger Werte über Milliarden Dokumente hinweg wäre speichertechnisch kaum zu vertreten. Die Cardinality Aggregation löst dieses Problem mit dem HyperLogLog++-Algorithmus, der die Anzahl eindeutiger Werte mit konstantem, sehr geringem Speicherbedarf approximiert, statt jeden Wert einzeln zu merken. Der Parameter precision_threshold entscheidet dabei, wie eng Genauigkeit und Speicherverbrauch beieinander liegen, und dieser Beitrag zeigt, wann die entstehende Fehlerquote fachlich völlig unproblematisch ist.

18 Min. Lesezeit HyperLogLog++ · precision_threshold · Fehlerquote Elasticsearch 8.x · OpenSearch 2.x

1. Warum exakte Unique Counts teuer sind

Eine exakte Zählung eindeutiger Werte, etwa "wie viele verschiedene Nutzer haben diese Seite besucht", erfordert im naiven Ansatz, jeden einzelnen bereits gesehenen Wert vollständig zu speichern, um Duplikate zu erkennen. Bei einem Feld mit wenigen tausend eindeutigen Werten ist das trivial, bei einem Feld mit hunderten Millionen eindeutiger Werte, etwa Session-IDs auf einer stark frequentierten Website, würde eine exakte Zählung Gigabyte an Zwischenspeicher pro Aggregations-Request benötigen, verteilt über alle beteiligten Shards.

Elasticsearch löst dieses Problem mit der Cardinality Aggregation, die statt einer exakten Zählung eine probabilistische Schätzung liefert. Anstatt jeden Wert vollständig zu speichern, verwendet die Aggregation einen Algorithmus, der aus jedem Wert einen Hash berechnet und daraus statistische Rückschlüsse auf die Gesamtanzahl eindeutiger Werte zieht. Der Speicherbedarf bleibt dabei nahezu konstant, unabhängig davon, ob tausend oder eine Milliarde eindeutige Werte vorliegen, ein fundamentaler Unterschied zu jedem exakten Zählverfahren.

2. HyperLogLog++ im Überblick

Der der Cardinality Aggregation zugrunde liegende Algorithmus heißt HyperLogLog++, eine von Google verbesserte Variante des ursprünglichen HyperLogLog-Algorithmus. Das Grundprinzip: Für jeden aggregierten Wert wird ein Hash berechnet, dessen Bitmuster statistische Informationen über die Verteilung eindeutiger Werte liefert. Konkret wird beobachtet, wie viele führende Nullen die Hash-Werte im Schnitt aufweisen; je mehr eindeutige Werte vorhanden sind, desto wahrscheinlicher wird ein Hash mit vielen führenden Nullen beobachtet. Aus dieser statistischen Beobachtung lässt sich die Gesamtanzahl eindeutiger Werte mit bemerkenswerter Genauigkeit zurückrechnen, ohne jemals einen einzelnen Wert vollständig zu speichern.

HyperLogLog++ verbessert den ursprünglichen Algorithmus insbesondere für kleine und mittlere Kardinalitäten, bei denen die reine HyperLogLog-Schätzung ungenau wird. Für kleine Wertemengen unterhalb eines internen Schwellwerts wechselt HyperLogLog++ intern zu einer linearen Zählung mit exakten Werten und geht erst bei größeren Mengen zur probabilistischen Schätzung über. Dieser hybride Ansatz sorgt dafür, dass die Cardinality Aggregation gerade im praxisrelevanten Bereich weniger Ausreißer produziert als die reine akademische HyperLogLog-Variante.


POST /web_logs/_search
{
  "size": 0,
  "aggs": {
    "unique_visitors": {
      "cardinality": {
        "field": "session_id.keyword"
      }
    }
  }
}
// Response excerpt:
// "aggregations": {
//   "unique_visitors": { "value": 4837291 }
// }
// Approximate count via HyperLogLog++, not an exact distinct count

3. precision_threshold verstehen und einstellen

Der Parameter precision_threshold steuert direkt, wie viel Speicher der HyperLogLog++-Algorithmus pro Aggregation verwendet und damit, wie genau das Ergebnis ausfällt. Konkret gibt precision_threshold die Anzahl eindeutiger Werte an, bis zu der die Cardinality Aggregation praktisch exakte Ergebnisse liefert. Oberhalb dieser Schwelle steigt der relative Fehler langsam an, bleibt aber auch bei sehr hohen Kardinalitäten in einem vorhersagbaren Rahmen. Der Standardwert liegt bei 3000, was für die meisten Anwendungsfälle mit moderater Kardinalität bereits ausreichend präzise Ergebnisse liefert.

Eine Erhöhung von precision_threshold verbessert die Genauigkeit, erhöht aber gleichzeitig den Speicherbedarf pro Aggregations-Bucket linear, bis zu einem internen Maximalwert von 40000. Dieser Trade-off wird besonders relevant, wenn eine Cardinality Aggregation als Sub-Aggregation innerhalb einer Terms Aggregation mit vielen Buckets läuft: Jeder einzelne Bucket erhält seine eigene HyperLogLog++-Struktur, sodass sich der Speicherbedarf mit der Anzahl der Buckets multipliziert, nicht nur mit dem gewählten precision_threshold.


POST /web_logs/_search
{
  "size": 0,
  "aggs": {
    "unique_visitors": {
      "cardinality": {
        "field": "session_id.keyword",
        "precision_threshold": 10000
      }
    }
  }
}
// precision_threshold trades memory for accuracy
// Values up to 10000 unique entries are near-exact

4. Fehlerquote und Speicherbedarf im Verhältnis

Die praktische Fehlerquote der Cardinality Aggregation liegt bei einem Standard-precision_threshold von 3000 üblicherweise unter 5 Prozent relativer Abweichung vom exakten Wert, selbst bei Kardinalitäten im zweistelligen Millionenbereich. Diese Fehlerquote ist keine feste Konstante, sondern schwankt statistisch um einen Erwartungswert, was bedeutet, dass wiederholte Abfragen auf identischen Daten geringfügig unterschiedliche, aber konsistent nahe beieinander liegende Werte liefern können, sofern sich die zugrunde liegenden Daten zwischenzeitlich nicht ändern.

Der Speicherbedarf pro HyperLogLog++-Struktur wächst mit steigendem precision_threshold, bleibt aber selbst bei sehr hohen Einstellungen im niedrigen einstelligen Kilobyte-Bereich pro Bucket, deutlich unter dem, was eine exakte Zählung mit derselben Kardinalität benötigen würde. Dieses Verhältnis aus minimalem Speicherbedarf und kontrollierbarer Fehlerquote macht die Cardinality Aggregation zur einzig praktikablen Lösung für Unique-Count-Analysen über sehr große Datenmengen, bei denen exakte Zählung schlicht nicht mehr möglich ist.

5. Wann Näherungswerte ausreichend sind

Näherungswerte der Cardinality Aggregation sind für die überwiegende Mehrheit der Analytics- und Monitoring-Anwendungsfälle vollkommen ausreichend. Eine Dashboard-Kachel, die "circa 4,8 Millionen eindeutige Besucher" anzeigt, verliert ihren fachlichen Wert nicht dadurch, dass die tatsächliche Zahl bei 4,75 oder 4,85 Millionen liegen könnte. Auch bei relativen Vergleichen über Zeit, etwa "eindeutige Nutzer diese Woche versus letzte Woche", heben sich systematische Abweichungen des Schätzverfahrens weitgehend auf, weil beide Werte mit demselben Algorithmus und derselben Einstellung berechnet werden.

Kritisch wird es dagegen bei Anwendungsfällen, die eine exakte, rechtlich oder finanziell verbindliche Zahl benötigen, etwa Abrechnungssysteme, die pro eindeutigem Nutzer abrechnen, oder Compliance-Reports mit gesetzlich vorgeschriebener Genauigkeit. In solchen Fällen ist die Cardinality Aggregation als alleinige Datenquelle ungeeignet, kann aber weiterhin als schnelle Vorabschätzung dienen, während die verbindliche Zahl über eine exakte Zählung, etwa via Terms- oder Composite Aggregation mit vollständiger Iteration, ermittelt wird.

6. Cardinality kombiniert mit Bucket-Aggregationen

Die Cardinality Aggregation entfaltet ihren größten Nutzen als Sub-Aggregation innerhalb einer Bucket-Aggregation, etwa um die Anzahl eindeutiger Besucher pro Landingpage oder pro Marketing-Kanal zu ermitteln. In Kombination mit einer Terms Aggregation auf channel.keyword liefert eine verschachtelte Cardinality Aggregation auf session_id.keyword in einem einzigen Request die eindeutige Besucherzahl für jeden Kanal, ohne dass die Anwendung für jeden Kanal einen separaten gefilterten Request stellen muss.

Bei dieser Kombination lohnt es sich besonders, den Speicherbedarf im Blick zu behalten: Bei zwanzig Kanälen und einem precision_threshold von 10000 entstehen zwanzig unabhängige HyperLogLog++-Strukturen gleichzeitig im Speicher. Bei einer hochkardinalitären Bucket-Aggregation mit hunderten Buckets kann diese Multiplikation spürbar werden, weshalb der precision_threshold bei stark verschachtelten Cardinality-Aggregationen bewusst niedriger gewählt werden sollte als bei einer einzelnen, globalen Cardinality-Abfrage.


POST /web_logs/_search
{
  "size": 0,
  "aggs": {
    "by_channel": {
      "terms": { "field": "channel.keyword", "size": 20 },
      "aggs": {
        "unique_visitors": {
          "cardinality": {
            "field": "session_id.keyword",
            "precision_threshold": 3000
          }
        }
      }
    }
  }
}
// One HyperLogLog++ structure per bucket
// Lower precision_threshold keeps total memory bounded

7. Cardinality vs. exakte Distinct-Count-Alternativen

Für Anwendungsfälle, die tatsächlich eine exakte Anzahl eindeutiger Werte benötigen, gibt es in Elasticsearch keine direkte, effiziente Alternative zur Cardinality Aggregation: Eine Terms Aggregation mit size gleich der erwarteten Kardinalität liefert zwar eine exakte Anzahl über buckets.length, materialisiert dabei aber jeden einzelnen Wert im Speicher, was bei hoher Kardinalität an dieselben Grenzen stößt, die zur Entwicklung der Cardinality Aggregation geführt haben. Eine vollständige Iteration über die Composite Aggregation liefert ebenfalls eine exakte Zahl, benötigt dafür aber deutlich mehr Requests und Zeit.

Außerhalb von Elasticsearch bleibt für exakte Zählungen häufig nur der Weg über eine relationale Datenbank mit COUNT(DISTINCT ...) auf einer separaten, aggregierten Tabelle, oder ein dediziertes Streaming-System, das exakte Zählung mit begrenztem Zeitfenster kombiniert. In der Praxis wählt man deshalb meist einen hybriden Ansatz: Cardinality Aggregation für Echtzeit-Dashboards und explorative Analysen, exakte Batch-Zählung für die wenigen Kennzahlen, bei denen absolute Präzision fachlich zwingend erforderlich ist.


// Approximate: cardinality aggregation, constant memory
POST /web_logs/_search
{
  "size": 0,
  "aggs": {
    "unique_visitors": { "cardinality": { "field": "session_id.keyword" } }
  }
}

// Exact: composite aggregation, full iteration required
POST /web_logs/_search
{
  "size": 0,
  "aggs": {
    "visitors": {
      "composite": {
        "size": 1000,
        "sources": [
          { "session": { "terms": { "field": "session_id.keyword" } } }
        ]
      }
    }
  }
}
// Count buckets across all pages for the exact number

8. Monitoring und Validierung der Genauigkeit

Um Vertrauen in die Genauigkeit der Cardinality Aggregation für einen konkreten Anwendungsfall aufzubauen, empfiehlt sich ein einmaliger Validierungslauf: Für eine überschaubare Teilmenge der Daten wird sowohl eine exakte Zählung, etwa über eine vollständige Composite-Aggregation-Iteration, als auch die Cardinality Aggregation mit dem produktiv geplanten precision_threshold ausgeführt und die Abweichung gemessen. Dieser einmalige Abgleich zeigt konkret, wie groß der tatsächliche Fehler in der eigenen Datenlandschaft ausfällt, statt sich auf generische Herstellerangaben zu verlassen.

Für den produktiven Dauerbetrieb reicht in der Regel eine grobe Plausibilitätsprüfung: Steigt oder fällt die geschätzte Kardinalität sprunghaft und unerwartet zwischen zwei aufeinanderfolgenden Zeitfenstern, deutet das eher auf ein Datenproblem als auf eine Schwäche des Schätzverfahrens hin, da HyperLogLog++ bei stabilen Datenmengen naturgemäß stabile Schätzwerte liefert. Ein Monitoring-Alert auf ungewöhnliche Sprünge in der Cardinality-Metrik ist deshalb ein nützlicher Nebeneffekt der Aggregation, unabhängig von ihrer primären fachlichen Nutzung.


// Compare estimated vs. exact on a bounded validation subset
POST /web_logs/_search
{
  "size": 0,
  "query": {
    "range": { "timestamp": { "gte": "2026-07-01", "lt": "2026-07-02" } }
  },
  "aggs": {
    "estimated": {
      "cardinality": {
        "field": "session_id.keyword",
        "precision_threshold": 3000
      }
    }
  }
}
// Run the same range with a full composite export,
// then diff the two counts to know your real error rate

9. precision_threshold-Einstellungen im Vergleich

Die folgende Tabelle zeigt typische Einstellungen und ihre Auswirkungen.

precision_threshold Speicher pro Bucket Typischer Fehler Einsatzfeld
1000 (Standard-Minimum) Wenige hundert Byte Höher, aber meist noch akzeptabel Viele parallele Buckets, grobe Schätzung
3000 (Standard) Wenige Kilobyte Unter 5 Prozent relativ Standard-Dashboards und Reports
10000 Wenige Kilobyte, höher Deutlich reduziert Einzelne globale Kennzahl, hohe Genauigkeit gewünscht
40000 (Maximum) Größter Speicherbedarf Minimal, nahe exakt Kritische Einzelmetrik ohne Verschachtelung

Die Wahl des richtigen precision_threshold ist damit eine bewusste Entscheidung zwischen Speicherverbrauch, insbesondere bei verschachtelten Aggregationen mit vielen Buckets, und der fachlich benötigten Genauigkeit. Für die meisten Anwendungsfälle ist der Standardwert von 3000 ein guter Ausgangspunkt, der nur bei konkretem Bedarf angepasst werden sollte.

Mironsoft

Elasticsearch-Analytics, Dashboards und Unique-Count-Metriken

Unique-Count-Metriken, die schnell und verlässlich genug sind?

Wir konzipieren Cardinality-basierte Dashboards, validieren die tatsächliche Fehlerquote in eurer Datenlandschaft und entscheiden gemeinsam mit euch, wo Näherungswerte reichen und wo exakte Zählung nötig ist.

Genauigkeits-Audit

Cardinality gegen exakte Zählung validieren, echten Fehler messen

Precision-Tuning

precision_threshold für Speicher- und Genauigkeitsbalance optimieren

Hybrid-Konzept

Näherungswerte für Dashboards, exakte Batch-Zählung für kritische Kennzahlen

10. Zusammenfassung

Die Cardinality Aggregation löst das Problem der Unique-Count-Berechnung über sehr große Datenmengen mit dem HyperLogLog++-Algorithmus, der eindeutige Werte über Hash-basierte statistische Schätzung approximiert, statt jeden Wert einzeln zu speichern. Der Speicherbedarf bleibt dabei nahezu konstant, unabhängig von der tatsächlichen Kardinalität, ein fundamentaler Vorteil gegenüber jeder exakten Zählmethode bei Millionen oder Milliarden eindeutiger Werte.

Der Parameter precision_threshold steuert das Verhältnis zwischen Genauigkeit und Speicherverbrauch, mit einem sinnvollen Standardwert von 3000, der bei den meisten Anwendungsfällen unter 5 Prozent relativer Abweichung liefert. Für Dashboards, Reports und explorative Analysen sind diese Näherungswerte in aller Regel vollkommen ausreichend. Nur bei rechtlich oder finanziell verbindlichen Zahlen sollte auf eine exakte Zählung über Terms- oder Composite Aggregation zurückgegriffen werden, gegebenenfalls ergänzt durch einen einmaligen Validierungslauf, der die tatsächliche Fehlerquote in der eigenen Datenlandschaft misst.

Cardinality Aggregation und Näherungswerte, das Wichtigste auf einen Blick

HyperLogLog++

Approximiert eindeutige Werte über Hash-Statistik mit nahezu konstantem Speicherbedarf, unabhängig von der Kardinalität.

precision_threshold

Standardwert 3000, steuert das Verhältnis zwischen Genauigkeit und Speicherbedarf pro Bucket.

Wann ausreichend

Dashboards, Reports, relative Vergleiche über Zeit. Nicht ausreichend für exakte Abrechnungen.

Verschachtelung

Jeder Bucket erhält eine eigene HyperLogLog++-Struktur, precision_threshold bei vielen Buckets bewusst niedriger wählen.

11. FAQ: Cardinality Aggregation und Näherungswerte

1Ist Cardinality Aggregation ein exakter Distinct Count?
Nein, eine probabilistische Näherung über HyperLogLog++. Für Analytics meist ausreichend, für rechtlich verbindliche Zahlen ungeeignet.
2Wie funktioniert HyperLogLog++?
Hash pro Wert, statistische Verteilung führender Nullen liefert die Gesamtanzahl, ohne jeden Wert einzeln zu speichern.
3Was macht precision_threshold?
Legt die Kardinalitätsgrenze für nahezu exakte Ergebnisse fest und steuert den Speicherbedarf, Maximum bei 40000.
4Wie hoch ist die typische Fehlerquote?
Bei precision_threshold 3000 üblicherweise unter 5 Prozent relative Abweichung, selbst bei Millionen Werten.
5Was passiert bei Verschachtelung in Terms Aggregation?
Jeder Bucket bekommt eine eigene Struktur, Speicherbedarf multipliziert sich. precision_threshold bei vielen Buckets senken.
6Wann exakte Zählung statt Cardinality?
Bei Abrechnung, gesetzlichen Reports oder finanzieller Verbindlichkeit. Composite Aggregation für vollständige Iteration nutzen.
7Liefert Cardinality bei Wiederholung denselben Wert?
Bei unveränderten Daten typischerweise denselben oder sehr nahen Wert, da die Schätzung deterministisch ist.
8Warum exakte Zählung bei kleinen Kardinalitäten?
Reine HyperLogLog-Schätzung ist bei kleinen Mengen ungenau, deshalb wechselt HyperLogLog++ dort zu linearer, exakter Zählung.
9Wie validiere ich die Genauigkeit?
Einmaliger Vergleich mit exakter Zählung auf einer Teilmenge, etwa über vollständige Composite Aggregation.
10Für Alerting auf Datenanomalien geeignet?
Ja, stabile Datenmengen liefern stabile Schätzwerte, Sprünge deuten meist auf Datenprobleme hin.