Egocentric-10KApache-2.0 7,993 frames8 workersfactory 051

What fraction of a video corpus is content it already contains?

Deduplication tools are mature and mostly free. What they report is a corpus-level number — and on this corpus that number hides a 6× spread between the individual people who shot the footage.

Method validated The redundancy figure is measured on one factory, but the embedding it relies on is now confirmed across six physically distinct factories: zero of 20,000 cross-factory pairs register as duplicates. What remains untested is whether the figure generalises, not whether the method is sound.

What already exists 01

Near-duplicate detection is not an open problem. Before any of the below is useful, it is worth knowing what ships today:

toolcapabilityavailability
FiftyOnefind_duplicates, uniqueness scoringopen source, 2.8M installs
Cleanlab Datalabnear-duplicate detectionopen source
Encord ActiveUniqueness metric, side-by-side reviewcommercial
Lightlycuration and selectioncommercial

To deduplicate an image dataset, use one of those. What follows is narrower: the same measurement split by who captured the footage, two gates that refuse to report a figure the embedding cannot support, and the confounds that turned up on the way — published rather than omitted.

The measurement 02

A frame is redundant at threshold t if its cosine similarity to any earlier frame in the corpus is at least t.

That definition is computed threshold-independently, which matters more than it sounds. One pass records each frame's best match against everything preceding it, and the entire curve derives from that single array. The obvious alternative — greedily keeping or dropping frames — has to be re-run per threshold, and its answer depends on the order in which drops cascade. That is a hidden knob, and a number resting on a hidden knob does not survive a skeptic.

0255075100 27.2% @ 0.92 0.800.850.880.900.920.940.960.98 cosine similarity threshold

Share of sampled keyframes whose content already appeared earlier in the corpus, after dropping the blurriest 20%. Global scope, 6,394 frames.

At a conservative threshold, 27.2% of frames duplicate earlier content — 95% CI [24.6%, 29.9%]. Redundancy is almost entirely self-redundancy: within-worker measures 27.2% and the global figure is also 27.2%. Workers repeat themselves. They do not duplicate each other.

corpus redundancy
Share of frames whose cosine similarity to any earlier frame in the same corpus meets a stated threshold.
operator spread
Ratio between the highest and lowest per-operator redundancy in a corpus. Measured here at 6.2×.
marginal novelty
Share of a clip's frames that are novel against everything that operator has already delivered.

On that interval. The obvious tool — bootstrap over clips — is invalid for this statistic. Resampling with replacement puts the same clip in the corpus twice, and this metric measures duplication, so every repeated clip scores as a perfect match against its own copy. The first attempt returned a 95% interval of [49.2%, 53.4%] around a 27.2% estimate: an interval that cannot contain its own point, because the method manufactured what it was measuring. The figure above is a jackknife, which never duplicates anything.

The average is the least useful number here 03

Redundancy ranges from 7.4% to 46.0% depending on which operator's footage you bought — a 6.2× spread around the corpus mean.

w00123.8%w00232.4%w00346.0%w0047.4%w00532.1%w00622.9%w00721.8% corpus mean 27.2%

Per-operator redundancy, same threshold and blur gate throughout. Standard deviation 11.9 points.

That spread is roughly 39 points wide, an order of magnitude larger than the ±2.7-point sampling error on the mean. Which means the corpus average — the number this whole exercise set out to produce — is the wrong unit of analysis. A buyer paying a flat rate per hour is exposed to whose footage they received far more than to any property of the corpus.

The commercial implication is not "audit corpora." It is price per operator.

Does buying more hours stop paying? 04

The natural follow-up: if an operator repeats themselves, there should be a point where their next clip adds nothing. So — for each clip in collection order, what share of its frames are novel against everything that operator has already delivered?

0255075100 11121314151 tail average 73% clip number, per operator

Marginal novelty per clip, averaged across operators and weighted by frame count. Threshold 0.92, blurriest 20% dropped.

It does not collapse. Novelty falls from 100% to roughly 75% within the first ten clips and then holds there — clip 50 is still about as novel as clip 15. Across the whole sample, 79.2% of frames are novel against their operator's earlier output.

This was not the expected result, and it changes the advice. There is no saturation point to stop at within this volume. Redundancy behaves like a steady tax of roughly a quarter, not a cliff — so the question for a buyer is not when to stop buying but what rate they are paying, which loops back to the operator spread above.

Motion blur is a confound, not noise 05

This was not in the plan. It surfaced from rendering sampled pairs and actually looking at them — and it is the reason the sensitivity sweep below is published alongside the headline rather than produced on request.

Two near-identical frames of hands assembling a small white component on a green workbench
0.956 · same worker, 8 seconds apart genuine duplicate

Unambiguous. Same bench, same paper, same hands, same part.

Two heavily motion-blurred frames showing green smears with little discernible detail
0.906 · same worker, different clips blur artifact
Two frames of a worker in blue coveralls at the same station handling a bin of metal parts
0.872 · same worker, different clips genuine duplicate

The inversion. The 0.906 pair matches on shared blur — two fast camera sweeps smeared into green. The 0.872 pair is unmistakably the same workstation, same parts bin, same task. The metric ranked the artifact above the real repeat.

Blur destroys the detail that distinguishes frames, so blurred frames collapse toward each other in embedding space and register as duplicates of one another. Frames are now scored for sharpness — variance of the Laplacian — and the blurriest fraction is dropped before measurement.

Filtering blur raises measured redundancy, because it removes low-information noise rather than real repeats. A filter that moves the headline in the flattering direction is exactly the kind of choice a reader should distrust, so here is the whole sweep:

none23.6%7,993−5%24.7%7,593−10%25.7%7,193−20%27.2%6,394−30%27.3%5,595−40%27.4%4,796 blur gate frames measured

Redundancy at threshold 0.92 across blur-gate strengths. The figure moves 3.8 points end to end and plateaus past 20% — the cutoff is not carrying the claim.

Blur share is independently useful. Frames too blurred to distinguish are also too blurred to train on, whether or not they repeat.

Does the embedding see this footage? 06

The obvious objection: CLIP was trained on web photography, not fisheye industrial video. If factory interiors collapse into a narrow region of the embedding space, everything looks alike and the redundancy figure is measuring a blind spot rather than a corpus.

The corpus answers this itself. It spans 85 physically distinct factories, which is a free control: frames from different plants must be clearly less similar than frames from the same worker. Six factories were sampled to test it.

same worker0.77p99 0.94different factory0.61p99 0.80 threshold 0.92

Random-pair cosine similarity, 20,000 pairs per scope, across six factories. Dots mark mean, p95 and p99. Separation +0.155, and zero cross-factory pairs clear 0.92 — the threshold sits above the 99th percentile of same-worker pairs.

The pass criteria were written into validate.py before the gated data was accessible: separation above 0.10, and under 1% of cross-factory pairs clearing the threshold. Measured: 0.155, and 0.00%. Not one pair in twenty thousand.

A sharper version of the same question

Mean separation is a blunt instrument. The direct test: if the embedding had collapsed this footage, it could not tell workstations inside a single factory apart. So — can a linear classifier read a frame's embedding and name the station it came from?

w00192.7%n=286w00295.9%n=462w00386.1%n=418w00493.5%n=217w00599.7%n=352w00689.0%n=418w00795.5%n=264 chance 14.3%

Workstation identification, 7 classes, held-out split by clip so no clip appears on both sides — frames seconds apart would otherwise leak the answer. Overall accuracy 92.9% against 14.3% chance.

This is arguably a harder test than the cross-factory one: stations inside one plant resemble each other far more than two different plants do. Passing it at 92.9% says the embedding carries fine-grained discriminative structure on exactly this footage — which is the property the redundancy metric depends on.

What remains open. Each worker has their own fisheye intrinsics, so part of that signal may be lens rather than scene. And validating the method is not the same as validating the number: 27.2% is what factory 051 measures, and whether other plants land near it is a separate question this does not answer.

What this does not show 07

None of this is a criticism of the corpus or the people who built it. Repetitive manual work produces repetitive footage; that is a property of factories, not a failure of whoever pointed the camera. Egocentric-10K is open, documented and Apache-2.0, which is the only reason this analysis exists at all.

Questions this answers 08

How do you measure redundancy in a video training corpus?

Sample keyframes, embed each one, and for every frame record its highest cosine similarity to any earlier frame in the corpus. The share of frames above a chosen threshold is the redundancy figure. Computing it this way — one pass, best-match-against-everything-earlier — means the whole threshold curve derives from a single array, so the result does not depend on a cutoff picked in advance.

How much of a robotics training dataset is duplicate content?

On the one corpus measured here — 10,000 hours of factory-floor egocentric video — roughly a quarter, 27.2% with a 95% interval of [24.6%, 29.9%]. But the corpus figure is the wrong unit: individual operators in that same corpus ranged from 7.4% to 46.0%.

Should I filter blurry frames before measuring similarity?

Yes, and not only for image quality. Motion blur destroys the detail that distinguishes frames, so blurred frames match each other and register as duplicates of unrelated content. Measured here, a blur-only pair scored 0.906 while a genuine same-workstation pair scored 0.872 — the metric ranked the artifact above the real repeat. Score sharpness (variance of the Laplacian) and drop the blurriest fraction first.

Can I use bootstrap resampling for a confidence interval on this?

No. Resampling with replacement puts the same clip in the corpus twice, and this statistic measures duplication — so every repeated clip scores as a perfect match against its own copy. Attempted here, it returned a 95% interval of [49.2%, 53.4%] around a 27.2% estimate. Use a jackknife, which never duplicates anything.

Does buying more hours from the same operator stop paying?

Not within the range measured. Marginal novelty falls from 100% to roughly 75% within the first ten clips and then holds flat through clip 52. Redundancy behaves like a steady tax of about a quarter, not a saturation cliff — so the actionable question is what rate you are paying, which depends on which operator you bought from.

How do I know the embedding is valid on my own footage?

Check two things before trusting any figure. First, saturation: what share of random frame pairs already clears the duplicate threshold? Real footage measured 0.03% at a 0.647 median; a synthetic corpus that broke the metric measured 26.2% at a 0.904 median. Second, separability: can a linear model name the operator from a single frame? Below about 2× chance, the embedding is not resolving the footage. Both are implemented as hard gates in the tool below.

Reproduce it 09

Runs on a GTX 1050 Ti in about an hour, network-bound. Nothing is downloaded: shards stream from the Hub, frames decode in memory, only embeddings persist.

git clone https://github.com/eitanp214/episcore.git
cd episcore
pip install -r requirements.txt
python src/pipeline.py --tag myrun --source subset

Source, tests and full method notes: github.com/eitanp214/episcore

The validation gate blocks the report if the embedding fails to discriminate on your footage. That is deliberate, and not skippable from the entry point.