Chart · milliseconds
sort, as a permutation.
neo 1.04 ms in the language study, 1.03 ms in the library run. Closest: Rust at 1.07×. Farthest: pandas at 62.7×.
Embed anywhere.
<iframe src="https://n0.is/embed/chart/sort-perm" title="sort, as a permutation" width="100%" height="520" loading="lazy" sandbox="allow-scripts" referrerpolicy="no-referrer" style="border:0;border-radius:12px"></iframe>Every engine's multiple of neo
- neo1×
- Rust1.07× · 1.11 vs 1.04
- Swift1.10× · 1.14 vs 1.04
- Zig1.34× · 1.39 vs 1.04
- Go1.43× · 1.49 vs 1.04
- Polars6.47× · 6.68 vs 1.03
- pandas62.7× · 64.8 vs 1.03
Bars to scale, from zero to the slowest engine. The gray pair is the engine's measurement and neo's in the same run, in ms. The languages and the libraries were measured in separate runs, so neo has a number in each; every multiple is against neo in its own run.
What this measures
Produce the stable ascending order of the amount column as a permutation of row indices, without moving any other column. SQL engines have no such form, so DuckDB and Spark sit this one out.
What neo is held to
A stable ascending order under the JavaScript rule that NaN sorts first and ties keep their place. The first sorted values are printed and compared with every other engine's.
Each side, this kernel only
Rust1.07× neo · neo vs Rust
Written in-house; it stays with the engine. How it was run and checked is on its comparison page.
Swift1.10× neo · neo vs Swift
Written in-house; it stays with the engine. How it was run and checked is on its comparison page.
Zig1.34× neo · neo vs Zig
Written in-house; it stays with the engine. How it was run and checked is on its comparison page.
Go1.43× neo · neo vs Go
Written in-house; it stays with the engine. How it was run and checked is on its comparison page.
Polars6.47× neo · neo vs Polars
timed("sort_perm", lambda: df["amount"].arg_sort())pandas62.7× neo · neo vs pandas
timed("sort_perm", lambda: np.argsort(amount.to_numpy(), kind="stable"))neo · confidential
neo's kernels, the ports written in-house to beat them, and the techniques behind both stay with the engine. Nothing about how the numbers were made is withheld: the method, the checks every engine had to pass, every number and every place neo is behind are on this page. The engine itself we keep confidential, because we don't want it getting into the wrong hands. The binaries run on request and reproduce every number here.
Measured on Apple M5 Max, 18 cores, 26.4.1, 2026-10-11 and 2026-10-15. Every number here is also on the comparison page of its engine, with how it was taken and the caveats.