When an agent writes, runs and repairs most of your code, a language choice becomes a token budget. The usual claim is that terse languages are cheaper. I wanted to see how much of that survives contact with real programs, so I wrote the same programs in seven languages, ran every one of them, and counted the tokens.
Short version: the gap between languages is real but much smaller than toy examples suggest, DSLs and libraries beat any general-purpose language on leverage, and the number that decides your bill, iterations to green, is one I could not measure from here.
An agent reads context, writes a change, runs it, reads the errors, and repeats.
Cached input is billed at a discount, so re-reading context is cheaper than it looks. That leaves output tokens and the number of passes as the terms that matter. A language touches all three levers: how much code a task needs, how big the error output is, and how often the first attempt is right. Public discussion mostly covers the first. I measured the first and part of the second.
Two programs, each in seven languages:
Each exists twice. The minimal version is the shortest reasonable program. The production version adds an optional N argument with validation, a URL argument, a 10 second timeout, non-zero exit codes and deterministic tie-breaking, with the same spec in every language. All 46 output and exit-code checks pass. The HTTP programs ran against a local server, including a 500 response.
| Language | Minimal (word freq + HTTP) | Production (word freq + HTTP) | Production total | vs Python |
|---|---|---|---|---|
| Python | 37 + 36 | 123 + 127 | 250 | 1.00x |
| Node.js | 100 + 41 | 179 + 104 | 283 | 1.13x |
| PHP | 76 + 54 | 162 + 130 | 292 | 1.17x |
| TypeScript | 123 + 56 | 211 + 129 | 340 | 1.36x |
| Rust | 157 + 88 | 257 + 199 | 456 | 1.82x |
| Java | 144 + 170 | 224 + 245 | 469 | 1.88x |
| Go | 150 + 135 | 282 + 207 | 489 | 1.96x |
Tokens are o200k_base. cl100k_base agrees within 8%.
What I take from it:
if err != nil. Rust's ? operator recovers some of that.reqwest and serde carry the work.Top three customers by revenue from an orders table:
SQL needs 27 tokens. Java needs 158, about six times as many, and plain Python needs 62. Note that pandas, a Python library, lands at 31. The leverage comes from the declarative shape, not the host language: say what you want and let a mature engine own the loop, the grouping and the sort. It is also the smallest surface to debug. If SQL, a regex, jq or a schema fits the problem, have the model write that.
I planted one misspelled variable in the word-frequency program in each language and counted the tokens in what the toolchain printed.
So verbose does not mean chatty, and the longest output came from a dynamic language. Two caveats matter. This is one trivial typo, and I did not measure ownership, lifetime or generic errors, which can be much longer. And a compiler only reports the bugs it can see. Logic errors pass it silently, so the cost that remains is your test output, in any language.
Everything above is the price of one pass. The bill is passes times price, and the number of passes depends on things a token counter cannot see.
My guess is that iterations dominate code size, but this benchmark cannot show it. Do not read the table as a ranking of cost.
pytest -q --tb=short, cargo check --message-format short.The programs, the runner with its 46 checks, the counting script and the typo test are in token-language-benchmark.zip. The tokenizers are OpenAI's, not Claude's, so recount with yours.
The experiment that would settle it is one I have not run: give an agent the same spec in each language, run it several times, and total input, cached and output tokens plus the passes to green. Report the median and the spread. If you run it, that is the number I would like to see.