Spaces:
Running
Running
| """ANSWER: the join of scene, agent, participants and events. No text. | |
| The user's definition, verbatim: "answer is just a join... everything is | |
| just logical." So this module contains no text tower, no fitted weight, | |
| no learned combiner - only the element tables and three logical | |
| operations: | |
| AND min over percentile ranks (scale-free conjunction) | |
| OR max over a candidate episode's objects | |
| BIND the AND is evaluated PER CANDIDATE OBJECT - "an object that | |
| looks like X and moves like X" must be satisfied by one | |
| object, not by one object that looks right and a different | |
| one that moves right. This binding is the entire difference | |
| between a join and a channel soup, and it is what "object1 | |
| (and similar) undergoing action1 (and similar)" means. | |
| Percentile ranks, not raw cosines, because the terms live on different | |
| scales (DINOv3 identity cosine, path-delta cosine, V-JEPA cosine) and a | |
| min over raw scales lets the tightest-distributed term govern | |
| everything. Rank-normalising is order statistics, not a weight. | |
| Element terms per query participant, each one a table: | |
| looks object_vectors DINOv3 track descriptor cosine | |
| moves trajectories signed, speed-normalised (dx,dy,dz) path | |
| deltas resampled to N steps - direction | |
| survives, which is the thing text erases | |
| acts vjepa_part physics tubelet cosine, where both sides | |
| have one | |
| Episode-level terms: | |
| scene scene_vectors pooled window cosine, one more rank in the | |
| conjunction | |
| events kind overlap a PARTITION, not a score: episodes sharing | |
| at least one event kind with the query rank | |
| ahead of episodes sharing none. Logical | |
| precedence, no number invented. | |
| """ | |
| from __future__ import annotations | |
| import numpy as np | |
| _C = {} | |
| NPATH = 16 # path resample steps; 15 deltas x 3 dims | |
| def _ranks(x): | |
| """Percentile rank in [0,1] per entry; NaN stays NaN (missing).""" | |
| x = np.asarray(x, np.float64) | |
| out = np.full(len(x), np.nan) | |
| ok = np.isfinite(x) | |
| if ok.sum() > 1: | |
| r = x[ok].argsort().argsort() | |
| out[ok] = r / (ok.sum() - 1) | |
| elif ok.sum() == 1: | |
| out[ok] = 1.0 | |
| return out | |
| def _path_desc(ts, px, py, pz, diag): | |
| """Signed, speed-normalised path deltas. Translation-invariant by | |
| construction (deltas), scale-normalised by the object's own box | |
| diagonal, direction preserved (open vs close differ by SIGN, the | |
| one thing appearance embeddings collapse - cos 0.957 measured).""" | |
| if len(ts) < 3: | |
| return None | |
| o = np.argsort(ts) | |
| t = np.linspace(0, len(o) - 1, NPATH).round().astype(int) | |
| x, y, z = (np.asarray(v, np.float64)[o][t] for v in (px, py, pz)) | |
| d = np.stack([np.diff(x) / max(diag, 1.0), | |
| np.diff(y) / max(diag, 1.0), | |
| np.diff(z) * 4.0], 1).ravel() | |
| n = np.linalg.norm(d) | |
| return (d / n).astype(np.float32) if n > 1e-6 else None | |
| def _elements(store): | |
| """Every element table, loaded once per store version, joined on | |
| the track key (stream, track_ts, t1, object_id).""" | |
| ver = store.table("trajectories").state().version | |
| key = (str(store.dir), ver) | |
| if key in _C: | |
| return _C[key] | |
| E = {} | |
| tr = store.table("trajectories").scan().to_pydict() | |
| by = {} | |
| for i in range(len(tr["ts"])): | |
| k = (str(tr["stream"][i]), int(tr["track_ts"][i]), | |
| int(tr["t1"][i]), int(tr["object_id"][i])) | |
| by.setdefault(k, []).append(i) | |
| paths, agents = {}, {} | |
| for k, idx in by.items(): | |
| bx = [(tr["x1"][i] - tr["x0"][i], tr["y1"][i] - tr["y0"][i]) | |
| for i in idx] | |
| diag = float(np.median([np.hypot(w, h) for w, h in bx])) | |
| d = _path_desc([tr["ts"][i] for i in idx], | |
| [tr["px"][i] for i in idx], | |
| [tr["py"][i] for i in idx], | |
| [tr["pz"][i] for i in idx], diag) | |
| if d is not None: | |
| paths[k] = d | |
| if any(tr["is_agent"][i] for i in idx): | |
| agents[k] = True | |
| E["paths"] = paths | |
| # key -> ROW index; double-detection twins share a key, so the | |
| # dict is smaller than the table and the reshape must use the ROW | |
| # count - keying by len(dict) sheared the matrix off by 2,086 rows | |
| ov = store.table("object_vectors").scan().to_pydict() | |
| E["obj"] = {(str(s), int(a), int(b), int(o)): i for i, (s, a, b, o) | |
| in enumerate(zip(ov["stream"], ov["ts"], ov["t1"], | |
| ov["object_id"]))} | |
| V = np.asarray(ov["vector"], np.float32).reshape(len(ov["ts"]), -1) | |
| E["objV"] = V / np.maximum( | |
| np.linalg.norm(V, axis=1, keepdims=True), 1e-8) | |
| vp = store.table("vjepa_part_vectors").scan().to_pydict() | |
| E["phys"] = {(str(s), int(a), int(b), int(o)): i for i, (s, a, b, o) | |
| in enumerate(zip(vp["stream"], vp["ts"], vp["t1"], | |
| vp["object_id"]))} | |
| Vp = np.asarray(vp["vector"], np.float32).reshape(len(vp["ts"]), -1) | |
| E["physV"] = Vp / np.maximum( | |
| np.linalg.norm(Vp, axis=1, keepdims=True), 1e-8) | |
| sc = store.table("scene_vectors").scan().to_pydict() | |
| E["scene"] = (sc["stream"], np.asarray(sc["ts"], np.int64), | |
| np.asarray(sc["vector"], np.float32) | |
| .reshape(len(sc["ts"]), -1)) | |
| ev = store.table("events").scan().to_pydict() | |
| E["events"] = ev | |
| E["agents"] = agents | |
| # EVENT-LEVEL join arrays: each event row -> its motion vector, its | |
| # bound object's DINOv3 descriptor row, its physics row, its | |
| # episode. The image-plane path descriptor above measured 0.08 | |
| # yield on the direction queries - 2D geometry does not survive a | |
| # camera change, and the supports span four cameras. The per-event | |
| # delta-appearance vector does (it is appearance change, not | |
| # coordinates), so it is the join's moves-term; geometry remains | |
| # the fallback where a window has no bound events. | |
| mv = store.table("motion_vectors").scan().to_pydict() | |
| mrow = {(str(s), int(a), int(b)): i for i, (s, a, b) in | |
| enumerate(zip(mv["stream"], mv["ts"], mv["t1"]))} | |
| MV = np.asarray(mv["vector"], np.float32).reshape(len(mv["ts"]), -1) | |
| MV /= np.maximum(np.linalg.norm(MV, axis=1, keepdims=True), 1e-8) | |
| tracks_of = {} | |
| for k in paths: | |
| tracks_of.setdefault((k[0], k[3]), []).append(k) | |
| n_ev = len(ev["ts"]) | |
| e_m = np.full(n_ev, -1) | |
| e_obj = np.full(n_ev, -1) | |
| e_phys = np.full(n_ev, -1) | |
| for i in range(n_ev): | |
| s, a, b = str(ev["stream"][i]), int(ev["ts"][i]), int(ev["t1"][i]) | |
| e_m[i] = mrow.get((s, a, b), -1) | |
| oid = int(ev["object_id"][i]) | |
| if oid >= 0: | |
| for k in tracks_of.get((s, oid), ()): | |
| if k[1] <= b and a <= k[2]: | |
| e_obj[i] = E["obj"].get(k, -1) | |
| e_phys[i] = E["phys"].get(k, -1) | |
| break | |
| # THE AGENT HAS NO LOOKS-TERM. Its identity is the ROLE - the | |
| # self-moving thing - not an appearance. Measured: agent-track | |
| # descriptors cosine 0.477 median against each other, barely | |
| # above random non-agent pairs at 0.437, because an articulated | |
| # arm deforms; only 0.2% of same-arm pairs clear the identity | |
| # cut, which is where 1,517 ids for ~4 arms came from. No | |
| # threshold merges what does not separate, so an agent event | |
| # matches by moves and physics alone, and its appearance rank - | |
| # noise by measurement - never enters the conjunction. | |
| if (ev["role"][i] == "agent" | |
| or (oid >= 0 and oid == int(ev["agent_object_id"][i]))): | |
| e_obj[i] = -1 | |
| E["e_m"], E["e_obj"], E["e_phys"], E["MV"] = e_m, e_obj, e_phys, MV | |
| ep = store.table("episodes").scan().to_pydict() | |
| E["episodes"] = [(str(s), int(a), int(b)) for s, a, b in | |
| zip(ep["stream"], ep["ts"], ep["t1"])] | |
| if len(_C) > 4: | |
| _C.clear() | |
| _C[key] = E | |
| return E | |
| def _tracks_in(E, stream, t0, t1): | |
| return [k for k in E["paths"] | |
| if k[0] == stream and k[1] <= t1 and t0 <= k[2]] | |
| def _scene_vec(E, stream, t0, t1): | |
| ss, ts, V = E["scene"] | |
| m = np.array([s == stream and t0 <= t <= t1 | |
| for s, t in zip(ss, ts)]) | |
| if not m.any(): | |
| return None | |
| v = V[m].mean(0) | |
| return v / (np.linalg.norm(v) + 1e-8) | |
| def answer_like(store, stream, t0, t1): | |
| """Episodes telling the same story as the query window. | |
| Returns (keys, score, shared_kind) - score is the conjunction rank | |
| (higher = better), shared_kind marks the event-kind partition. | |
| """ | |
| E = _elements(store) | |
| eps = E["episodes"] | |
| n = len(eps) | |
| # ---- the query's elements ----------------------------------- | |
| q_tracks = _tracks_in(E, stream, t0, t1) | |
| ev = E["events"] | |
| q_kinds = {ev["kind"][i] for i in range(len(ev["ts"])) | |
| if str(ev["stream"][i]) == stream | |
| and int(ev["ts"][i]) >= t0 and int(ev["t1"][i]) <= t1 | |
| and ev["kind"][i]} | |
| ep_of = {} | |
| for i, (s, a, b) in enumerate(eps): | |
| ep_of.setdefault(s, []).append((a, b, i)) | |
| # events of the query window, and each event's episode index | |
| q_ev = [i for i in range(len(ev["ts"])) | |
| if str(ev["stream"][i]) == stream | |
| and int(ev["ts"][i]) >= t0 and int(ev["t1"][i]) <= t1] | |
| n_ev = len(ev["ts"]) | |
| ev_ep = np.full(n_ev, -1) | |
| for i in range(n_ev): | |
| s, a = str(ev["stream"][i]), int(ev["ts"][i]) | |
| for ea, eb, j in ep_of.get(s, ()): | |
| if a >= ea and a <= eb: | |
| ev_ep[i] = j | |
| break | |
| # ---- EVENT-LEVEL join (primary) ----------------------------- | |
| # "the same transition happening to the same kind of thing": per | |
| # query event, every candidate event is scored on moves (delta- | |
| # appearance of the transition - the view-tolerant motion term; | |
| # image-plane geometry measured 0.08 on the direction queries | |
| # because the supports span four cameras) AND looks (DINOv3 of the | |
| # object each event BINDS to) AND acts (its physics tubelet). One | |
| # candidate event must satisfy all of it - that is the join. | |
| # conjunction granularity is the KIND, not the event instance: a | |
| # window holding five t3 relocations and one t7 asks for "t3-like | |
| # AND t7-like", not six independent demands. OR (max) within a | |
| # kind's query events, AND (min) across kinds - the story's clauses | |
| # are its distinct transitions. | |
| q_bound = [i for i in q_ev if E["e_m"][i] >= 0] | |
| by_kind = {} | |
| for qi in q_bound: | |
| by_kind.setdefault(ev["kind"][qi] or "", []).append(qi) | |
| per_kind = [] | |
| for kind, members in by_kind.items(): | |
| rows = [] | |
| for qi in members: | |
| terms = [] | |
| terms.append(_ranks(E["MV"] @ E["MV"][E["e_m"][qi]])) | |
| if E["e_obj"][qi] >= 0: | |
| qv = E["objV"][E["e_obj"][qi]] | |
| sims = np.full(n_ev, np.nan) | |
| has = E["e_obj"] >= 0 | |
| sims[has] = E["objV"][E["e_obj"][has]] @ qv | |
| terms.append(_ranks(sims)) | |
| if E["e_phys"][qi] >= 0: | |
| qv = E["physV"][E["e_phys"][qi]] | |
| sims = np.full(n_ev, np.nan) | |
| has = E["e_phys"] >= 0 | |
| sims[has] = E["physV"][E["e_phys"][has]] @ qv | |
| terms.append(_ranks(sims)) | |
| with np.errstate(invalid="ignore"): | |
| bound = np.nanmin(np.stack(terms), 0) | |
| row = np.full(n, np.nan) | |
| for i in range(n_ev): | |
| e = ev_ep[i] | |
| if e >= 0 and np.isfinite(bound[i]): | |
| row[e] = bound[i] if np.isnan(row[e]) \ | |
| else max(row[e], bound[i]) | |
| rows.append(row) | |
| with np.errstate(invalid="ignore"): | |
| per_kind.append(np.nanmax(np.stack(rows), 0)) | |
| if per_kind: | |
| with np.errstate(invalid="ignore"): | |
| score = np.nanmin(np.stack(per_kind), 0) # AND across kinds | |
| score = np.where(np.isnan(score), 0.0, score) | |
| else: | |
| # ---- track-path fallback: a window with no bound events ---- | |
| all_keys = list(E["paths"].keys()) | |
| P = np.stack([E["paths"][k] for k in all_keys]) | |
| track_ep = np.full(len(all_keys), -1) | |
| for i, k in enumerate(all_keys): | |
| for a, b, j in ep_of.get(k[0], ()): | |
| if k[1] >= a and k[1] <= b: | |
| track_ep[i] = j | |
| break | |
| q_parts = [k for k in q_tracks if E["agents"].get(k)] or q_tracks | |
| if not q_parts: | |
| return eps, np.zeros(n, np.float32), np.zeros(n, bool) | |
| per = [] | |
| for qk in q_parts: | |
| bound = _ranks(P @ E["paths"][qk]) | |
| row = np.full(n, np.nan) | |
| for i, e in enumerate(track_ep): | |
| if e >= 0 and np.isfinite(bound[i]): | |
| row[e] = bound[i] if np.isnan(row[e]) \ | |
| else max(row[e], bound[i]) | |
| per.append(row) | |
| with np.errstate(invalid="ignore"): | |
| score = np.nanmin(np.stack(per), 0) | |
| score = np.where(np.isnan(score), 0.0, score) | |
| qs = _scene_vec(E, stream, t0, t1) | |
| if qs is not None: | |
| ssims = np.full(n, np.nan) | |
| for i, (s, a, b) in enumerate(eps): | |
| v = _scene_vec(E, s, a, b) | |
| if v is not None: | |
| ssims[i] = float(v @ qs) | |
| sr = _ranks(ssims) | |
| with np.errstate(invalid="ignore"): | |
| score = np.fmin(score, np.where(np.isnan(sr), score, sr)) | |
| # ---- event-kind PARTITION ----------------------------------- | |
| shared = np.zeros(n, bool) | |
| if q_kinds: | |
| for i in range(len(ev["ts"])): | |
| k = ev["kind"][i] | |
| if k and k in q_kinds: | |
| s = str(ev["stream"][i]) | |
| a = int(ev["ts"][i]) | |
| for ea, eb, j in ep_of.get(s, ()): | |
| if a >= ea and a <= eb: | |
| shared[j] = True | |
| break | |
| return eps, score.astype(np.float32), shared | |