Tungsten — Pseudocode that runs. Public preview version 2026.07.04
PUBLIC PREVIEW · v2026.07.04
Object-oriented · self-hosted · LLVM + Metal
Pseudocode<br>that runs.
An object-oriented language that reads like the math on your whiteboard — then compiles, through a compiler written in itself, to native binaries via LLVM and GPU kernels via Metal. No end, no braces, no return. Fewer tokens for the humans and the models reading along.
Install Tungsten →<br>Read the Docs
$ curl -fsSL tungsten-lang.org/install | sh<br>Copy
demo.w
1# Currency and percentages<br>2price = $499.99<br>4 price - 15% # => ≈$424.99<br>5 price - 15% + 8.25% # => ≈$460.05<br>7# Units of measurement<br>8c = 299_792_458 m/s<br>9m = 1 kg<br>10<br>11 e = m·c² # => ≈8.988×10¹⁶ J<br>12<br>13 3 ft + 12 in # => 4 ft<br>14 10 ft * 10 ft # => 100 ft²<br>15 2 m + 2 lbs # => error: dimension mismatch
Why Tungsten
No ends. No braces.<br>Just the algorithm.
Tungsten strips programming to its mathematical essence. Write code that looks like the pseudocode you'd put on a whiteboard.
💰
Native Currency
First-class support for dollars, cents, and percentage operations. No more floating-point money bugs.
$3.50 - 25¢ # => $3.25
📐
Units That Catch Your Mistakes
Meters, feet, kilograms — with automatic conversion and dimensional analysis, so mismatched units fail loudly instead of becoming bad numbers.
1 cm * 1 cm * 1 cm # => 1 cm³
Math That Reads Like Math
Write mathematical notation directly. Square roots, superscript exponents, deltas — your code reads like the textbook.
√(Δx² + Δy² + Δz²)<br>3² + 4² # => 25
🧱
Classes Without Noise
Define classes with +, methods with ->, output with . Arity is explicit. Everything else melts away.
+ Point<br>-> new(@x, @y, @z) ro
🎯
Exact Decimals by Default
3.14 is an exact decimal, not an IEEE float. Approximation is opt-in with ~ — so the default never surprises your accountant.
exact = 3.14 # Decimal<br>approx = ~3.14 # Float, opt-in
🌀
Complex, Quaternions & Beyond
Complex numbers, quaternions, octonions, sedenions — one generic implementation, specialized per scalar type, all the way out to 256-dimensional algebras.
z = Complex.new([~3.0, ~4.0])<br>z.abs # => 5
The GPU Is One Annotation Away
@gpu fn compiles a Tungsten function to Metal Shading Language — same file, same syntax, no FFI, no strings of C.
@gpu fn add_one(x, y, n)<br>i = gpu.thread_position_in_grid.x
🧠
Tensors, Zero-Copy on Metal
One allocation, three faces: a CPU array, a Metal buffer, and tensor views when the platform supports them — sharing the same bytes. Attention runs end-to-end on-device.
q = x.linear(wq) # bf16, on the GPU<br>attn = scores.softmax(1)
🤖
Dense by Design
No end, no braces, no self, no return. Every keyword the syntax omits is a token neither you nor a model has to spend — so more algorithm fits in the same context window.
# the whole method, not the ceremony<br>-> area w * h
By Example
Read it like pseudocode
Concrete examples from the language surface — nine features, one tab each.
Classes<br>Blocks<br>Case / recase<br>Generics<br>GPU<br>Tensors<br>Math Modes<br>Currency<br>Physics
Classes Without the Noise
Define a class with +, a method with ->, and output with . Arity after the slash tells you exactly how many arguments a method takes.
Instance variables are declared inline in the constructor with @. The ro suffix makes them read-only. No boilerplate getters, no verbose accessor declarations.
The prime notation (x') refers to the same-named property on the argument — so x - x' means "my x minus their x." And Δx is that difference in one glyph: √(Δx² + Δy² + Δz²) is a distance method that runs.
point.w
1+ Point<br>2 -> new(@x, @y, @z) ro<br>4 -> distance/1<br>5 dx = x - x'<br>6 dy = y - y'<br>7 dz = z - z'<br>9 (dx.sq + dy.sq + dz.sq).sqrt<br>10<br>11 # or, if you prefer<br>12 -> distance/1<br>13 √(Δx² + Δy² + Δz²)<br>14<br>15 Point(3, 4, 0).distance(Point(0, 0, 0)) # => 5
Blocks With an Implicit Subject
A block is just -> followed by an expression, and inside it item is already bound. No pipes, no lambda keyword, no parameter list for the common case.
Block passthrough goes further: pass a trailing block to a method that doesn't take one, and the block iterates the method's result. bag.items -> s += item loops over what items returns.
Accumulator methods read like recurrences — -> sum 0 declares the initial value inline, and the body folds into it.
blocks.w
1# blocks bind `item` implicitly<br>2squares = [1, 2, 3].map -> item ** 2<br>3evens = (1..10).select -> item % 2 == 0<br>5 squares # => [1, 4, 9]<br>6 evens.sum # => 30<br>8# block passthrough: a trailing block on a<br>9# no-block method iterates its result<br>10+ Bag<br>11 -> items<br>12 [10, 20, 30]<br>13<br>14s = 0<br>15Bag.new().items -> s += item # s => 60<br>16<br>17# even `n.times` is just passthrough on an Int<br>18u = 0<br>19(-5).abs -> u += 1 # runs 5 times
Case, Meet recase
Dispatch with case/when, close blocks by dedent. When an arm needs to re-enter the decision with a new value, recase expr re-dispatches the enclosing case — structured, no goto, no loop...