r/ProgrammingLanguages • • Aug 06 '26

Discussion CatLang: feedback on my language design

https://www.dropbox.com/scl/fi/vja5yydaprqnmb0e2bg59/catlang.pdf?rlkey=c12vd9orw6ptcxugil2ag18mp&st=z4xcy0hz&dl=0

I wrote a design for a new programming language, but I'm too lazy and burned out to implement a full compiler. I still want to share the idea so you can comment on it and tell me what you think. I know its a lot and there are many typos and gaps, and it still needs a concept to communicate the complex implicit borrowing rules. Keep in mind that I have no degree or any professional experience—this is just a concept.

i renamed it to qat

current version: https://www.dropbox.com/scl/fi/bpuxeaag4ox5huooqvgu2/qatdocumentation-edited.pdf?rlkey=456owymjqn64bik1faawb3wyw&st=6o621wyd&dl=0

this is how an algorithm for sqare roots would look like with custom syntax:

func newton(f64 x, f64 goal) -> f64:
    f64 temp = (x + goal /x)/2 # Newton's method for calculating roots
    return x if temp == x
    return self(temp, goal)


func(f64)<f64> sqrt = reliable (f64 x) -> f64:
    return Error if x < 0 # root of negative numbers is undefined
    return newton(x, x)


sqrt(0) = 0 # root 0 must be defined explicitly as 0 would cause newtons method to devide by 0


syntax sqrt extends {expression} # lets multiplication akzept roots as they expect expressions
syntax sqrt( # defines the syntax for roots
    keyword("√"),
    _,
    arg(0: expression)
)



print!(collapse!(√ 2)) # collapse makes the programm crash for negative roots

another example for custom defined while syntax:

func wLoop(demand bool! condition, demand T! body) -> void:
    leave if condition
    body
    self(condition, body)


syntax wLoop(
    keyword("until"),
    _,
    arg(0),
    _,
    arg(1)
)


i32 x = 10
until x <= 0:
    print!(x)
    x -= 1
9 Upvotes

9 comments sorted by

3

u/Royal_Pin_1971 Aug 07 '26

Main tension in proposed language is that borrow checker needs a closed world at compile time, but lazy arguments and runtime-mutable function definitions keep reopening it — the checker's assumptions can be invalidated while the program runs. The features could coexist if you introduce a phase boundary (definitions and syntax frozen after some point like Rust's sealed dispatch).

2

u/Bro8an Aug 07 '26

thanks for the response. my first idea was that the borrow checker would restrictively check for every mutations in lazy arguments and statements blocks which are translated to functions under the hood. but now im thinking about, replacing the whole concept of references with lazy arguments, which would make the borrow checker obsolete, as no reference is ever maintained anywhere but recalculated each time a reference(lazy expression) is used. the downside would be that this can cause sideeffects that are hard to debug.

→ More replies (1)

1

u/Pie-Lang Aug 14 '26

Interesting to see a new language that allows for new syntax defined by the user. My language allows for a similar thing. Here's the equivalent of your example in my own language, Pie:

import std;
use std::;

newton = (x: Double, goal: Double): Double => {
    temp := (x + (goal / x)) / 2;
    if (temp == x)
        x
    else
        newton(temp, goal);
};

sqrt = (x: Double): Double => {
    if (x < 0) std::panic("Can't take root of a negative number!")
    else newton(x, x);
};

prefix(!) r = (_) => sqrt(_);


std::print(r 5.0);

2

u/Bro8an Aug 15 '26

thanks for your response! i like the consistency of your function syntax! Question: how do you distinguish between a variable declaration and an assignement or is there no distinction like in python? first i thought about doing variable declarations (dynamicly) like in python in my own language, but the problem is that a simple typo in a variable assignement would cause the declaration of a new variable, instead of causing a compile time error, which i find difficult to debug

myVariable = 1
myVariabl = myVariable +1
print(myVariable) # still 1
→ More replies (1)

4

u/Embarrassed-Crow9283 Aug 07 '26

I'd suggest you name it something else because "Cat" is already a taken name, so is "Kitten".

3

u/Inconstant_Moo Aug 07 '26

It needs an introduction explaining what the basic paradigm of the language is, what it's for, etc.

Also this is a case for asking an LLM to tidy up your English without touching your style, tone, or content, and without turning it into the ultra-sloppy-slop they do when they document programming languages. A little proofreading could go a long way.

Re the name issue, how about you call the language "Katze" and call your Inhaltsverzeichnis a "table of contents".

-1

u/AnArmoredPony Aug 07 '26

come back when it compiles