Distance to closest record (DCR)
What DCR measures, how it detects memorisation in synthetic data, why it needs a baseline, and how to read it with NNDR.
Updated 16 August 2026 · Figures from metrics engine 0.5.1
Distance to closest record is the simplest privacy metric for synthetic data and one of the most useful. It answers a direct question: for each synthetic row, how far away is the nearest real row? If the answer is "very close" for many rows, the generator did not learn the population — it copied individuals.
DCR belongs to the privacy pillar of synthetic data validation. It is a distance-based metric rather than an attack-based one, which means it needs no control group and can always run. It is also easy to misread without a baseline, and this page explains how to read it properly.
Definition
For each synthetic record, compute the distance to its nearest neighbour in the real dataset. DCR is the distribution of those distances across all synthetic records — usually summarised by its minimum, its lower percentiles (5th, for instance), and its median.
Distance requires a metric on mixed data. Numeric columns are scaled (so a salary in the hundreds of thousands doesn't dominate an age in the tens); categorical columns contribute a fixed distance for a mismatch (Gower distance is the standard choice, L1 on encoded features is common). Exact choices differ between tools, which is one reason DCR values are only comparable within one engine.
A DCR of zero for a synthetic row means an exact copy of a real row. Very small DCRs mean near-copies — a real record with one or two fields nudged.
Why it needs a baseline
Here is the mistake to avoid: reading raw DCR values as if small always means bad. It doesn't. In a dense region of the real data — many similar customers, many similar transactions — real rows sit close to each other, and a well-behaved synthetic row generated from that region will also sit close to some real row, without having copied any of them.
The fix is to compare against the real data's own structure. Compute the same nearest-neighbour distances within the real data (real to real, excluding self) and compare the two distributions. If synthetic-to-real distances look like real-to-real distances, the synthetic rows are as far from real individuals as real individuals are from each other: no leakage signal. If synthetic-to-real distances are systematically smaller than real-to-real, synthetic rows are hugging specific real records: memorisation.
This is also what the closely related nearest-neighbour distance ratio (NNDR) captures per row — the distance to the nearest real record divided by the distance to the second-nearest. A ratio near zero says the synthetic row is far closer to one real individual than to anyone else. Read DCR and NNDR together: DCR for the overall shape, NNDR for the individually suspicious rows.
What a bad score usually means
Memorisation. The generator overfit and is emitting training records with small perturbations. This is the classic failure of overparameterised generators trained too long on small data. It usually shows as a spike of near-zero DCRs — a chunk of rows that are essentially copies — while the rest of the distribution looks fine. Look at the lower tail, not the median.
Too little training data. With few real rows, the generator has nothing to learn but the rows themselves. DCR failures on small datasets are expected and mean "this data was not suitable for synthesis at this size," not "this generator is bad."
High-cardinality identifiers left in. A column of near-unique values — account IDs, timestamps to the second, free-text — makes every real row an outlier and forces the generator to reproduce or invent identifiers. Either way DCR becomes uninformative. Such columns should be removed or generalised before generation, and a validation report should flag them.
Legitimately dense data. Sometimes small DCRs reflect a real population with many near-identical records. This is why the baseline comparison matters: real-to-real distances will be equally small and the ratio will be unremarkable.
The remedy is generator-agnostic: regularise or stop earlier, drop or coarsen identifiers, and re-run — DCR is cheap enough to use as a check on every iteration.
Reading DCR alongside the other pillars
DCR is a necessary check, not a sufficient one. It catches direct copying and near-copying — the crudest leak — and it does so reliably and without a holdout. What it does not measure is subtler leakage: whether an attacker can infer a real person's sensitive attribute, or link records, or tell whether someone was in the training set. Those need attack-based metrics (singling-out, linkability and inference, membership inference) and, for full power, a control group. A dataset can pass DCR comfortably and still fail an inference attack.
Conversely, DCR is one of the two metrics that can never be reported as "not tested" for lack of a holdout — it always runs. If a privacy report shows only DCR-style distance metrics and calls the dataset private, it has measured the easy thing and skipped the hard one.
Worked example
UCI Adult census, 4,200 rows × 15 columns, SDV Gaussian Copula, metrics engine 0.6.0. Privacy pillar 98.5.
| Distance to closest record | Minimum | 1st pct | 5th pct | Median |
|---|---|---|---|---|
| Synthetic → real | 0.0914 | 0.2785 | 0.5342 | 1.4319 |
| Real → real (baseline) | 0.0011 | 0.0299 | 0.0773 | 0.7819 |
Read the baseline row first. Real records sit as close as 0.0011 to each other — near-duplicate people exist in census data, and a tool without a baseline would have to call that a leak or ignore it. The synthetic rows sit further from real records than real records sit from each other at every point in the distribution: the 5th percentile is 0.5342 against 0.0773, a ratio of 6.9. Nothing is hugging anyone.
The memorising-generator control run on the same data:
| Distance to closest record | Minimum | 1st pct | 5th pct | Median |
|---|---|---|---|---|
| Synthetic → real | 0.0000 | 0.0000 | 0.0000 | 0.0006 |
The lower tail is flat zero and the median is 0.0006 — practically the whole file is sitting on top of the source. All 4,200 of 4,200 rows are exact copies, and 2,157 of them (51.4%) are also within near-copy distance of a second real record. That run's privacy pillar scored 3.2 and its overall grade was capped at D.
NNDR flagged nothing on the SDV run: 57 of 4,200 rows (1.36%) came in below the anchoring threshold, against 18.57% for real records measured the same way — 17 points below baseline. On the memorising control the same measure reached 59.3%, or 40.7 points above it.
How SynthProof reports it
SynthProof reports DCR as a distribution — minimum, lower percentiles and median — for synthetic-to-real, side by side with the real-to-real baseline computed the same way, plus per-row NNDR flags for individually suspicious records. Exact-copy detection runs first as a separate check. These distance metrics always run, in every mode that includes a real sample; they are labelled explicitly as the part of the privacy pillar that does not depend on a holdout. When a memorisation pattern is detected, the findings name the affected rows' characteristics (not the rows themselves) and, where relevant, the high-cardinality columns that should be generalised before regeneration.
Related metrics
Nearest-neighbour distance ratio is DCR's per-row companion. Exact-copy detection is the degenerate case DCR generalises. Membership inference is what to run next when DCR passes and you need to know about subtler leakage.
Back to the guide: Synthetic data validation: the complete guide.