--- license: mit library_name: pytorch pipeline_tag: image-segmentation tags: - spatial-reasoning - path-finding - iterative-computation - vision-transformer - maps - amsterdam - from-scratch model-index: - name: spatial-wave-search-256m results: - task: type: path-finding name: route search on map layers, free-running on the network's own scratchpad dataset: type: custom name: De Pijp (Amsterdam) held-out validation routes, 500 routes, 40–500 m walking metrics: - type: solved-share name: "solved (cell rule: connected, no building cell, ≤ 1.10 × walking length)" value: 0.78 - type: solved-share name: "solved (polyline rule shared with the VLM baseline)" value: 0.76 - task: type: path-finding name: never-seen district (Zuid + Centrum), 500 validation routes dataset: type: custom name: Zuid + Centrum 256 m validation routes metrics: - type: solved-share name: "solved (cell rule)" value: 0.60 - task: type: path-finding name: zero-shot on a synthetic house maze dataset: type: custom name: house maze, 256 m windows, 500 validation routes metrics: - type: solved-share name: "solved (cell rule)" value: 0.51 --- # A 9 M-parameter transformer that runs a path search on its own scratchpad (256 m windows) ![A free-running search on a never-seen district](wave_search_256m_unseen_district_route342_295m.gif) *Figure. A free-running search by this network on a district it never saw (Zuid + Centrum, Amsterdam; 256 m window, 2 m cells): start and goal lie on opposite sides of one building, the route is 295 m, 2.4 × the straight line. Each frame is one pass; the orange cells are the network's whole output, fed back as its next input; its own state token (SEARCH → BACK → DRAW → DONE) picks the next pass.* The main result of [spatial-reasoning-from-scratch](https://github.com/Marvel4U/spatial-reasoning-from-scratch): a small vision transformer trained from scratch on spatially aligned city map layers runs a search over many passes, reading back only its own drawing, and solves **78 %** of 500 held-out routes (96 / 89 / 63 % for routes of 2–3 / 4–5 / 6+ fronts), **60 %** on a district it never saw and **51 %** on synthetic house mazes it never trained on. Under one shared rule it beats the same network drawing the path in one pass (37 %) and a Qwen3-VL-2B fine-tuned with LoRA on 19.3k of the same routes (50 %), and the gap grows with route length. It is **not** a vision-language model: input and output are rasters. ## What it does - **Input:** a 256 m × 256 m window drawn as 17 aligned planes at 1 m per pixel, two markers in a marker plane, and a scratchpad plane holding its own previous output. - **Output:** the whole next scratchpad on a 128 × 128 grid of 2 m cells, plus one state token. - **Algorithm learnt from a teacher** (one clearance-priced wave per route): spread a front 40 m further each pass until the goal is reached, then walk the way back front by front, then draw the path. One pass 2.4 ms on an RTX 3060; a route 57 ms (10 passes on average). ## Model and training 4 blocks, width 384, 6 heads, 16 px patches (256 tokens), learned relative position bias, two condition tokens (state, task), per-cell 2-class head and 41-class token head; 8.86 M parameters. 48k steps on 100k De Pijp routes (cosine, batch 128, pad noise, annealed change-cell weighting, token loss weight 0.1), then 16k steps with half of the input drawings replaced by the network's own stored drawings ("natural noise"), the target staying the teacher's. Run id `c5_r5_wave_nat3_tok01_ownp50_from48k_L4_16k_g128_store100k`. ## How to use ```bash git clone https://github.com/Marvel4U/spatial-reasoning-from-scratch # place this file as runs/checkpoints/c5_r5_wave_nat3_tok01_ownp50_from48k_L4_16k_g128_store100k.pt # unpack eval_bundle_v0.2.tar.gz of the GitHub release and copy its data/ and runs/ into the clone (REPRODUCE.md section 8) cd harness PYTHONPATH=. python diagnostics/wave_rollout_eval.py c5_r5_wave_nat3_tok01_ownp50_from48k_L4_16k_g128_store100k --n 500 --mode free PYTHONPATH=. python diagnostics/wave_rollout_gif.py c5_r5_wave_nat3_tok01_ownp50_from48k_L4_16k_g128_store100k --route 342 --crops ../data/amsterdam/zuid_centrum/crops/v4ns --store c4_256_val ``` ## Related models - [`mxv456/spatial-wave-search-512m-hero`](https://huggingface.co/mxv456/spatial-wave-search-512m-hero): the same network continued at 512 m windows (routes to 1.1 km; the maze animation of the repository's README and `PAPER.md`). - [`mxv456/qwen3-vl-2b-lora-map-routes`](https://huggingface.co/mxv456/qwen3-vl-2b-lora-map-routes): the vision-language baseline. ## Limitations One city for training; single seed; the headline depends on the route mix (75 % on the first 200 routes, 64 % before natural noise); the success rule scores the drawing as a set of cells, and a polyline extracted from it scores 76 %; long routes remain the failure mode. ## Citation and licence Marvin Uhlmann, *Spatial reasoning from scratch on real city data*, 2026, [github.com/Marvel4U/spatial-reasoning-from-scratch](https://github.com/Marvel4U/spatial-reasoning-from-scratch). Code and weights MIT; data licences in the repository's `DATA_LICENSES.md`.