Standard ML Family
smlfamily.github.io
smlfamily.github.io
Really shows the power for statically typed functional languages, and especially the power of sum types. Representing trees with sum types is so extremely powerful and makes writing compiler oriented code feel very natural. I haven't used it since graduation, but if I had to write a compiler, I'd probably opt for an SML like language, like F#.
And also WebML [2], SOSML [3], Bright-ML [4] (had to refresh my memory from my 2020 post on the topic [5]).
[0] http://blog.hydromatic.net/2020/02/25/morel-a-functional-lan...
[1] https://github.com/hydromatic/morel
[2] https://github.com/KeenS/webml
[3] https://github.com/SOSML/SOSML
Going off on a tangent, I think every language should require function parameters and return types to be explicitly typed. If that gets rid of the bulk of HM type inference that's cool. The only value to me of type inference is at the local variable level. Function type inference makes code impossible to read.
And the type errors very non-local and therefore hard to understand. The reason is that HM type inference infers types not only in the leaves->roots direction, but also roots->leaves. An expression gets assigned a type based on the context it appears in. It works wonderfully when the program type checks, because e.g. it allows one to write something like "let x = None" in Rust instead of "let x: Option<very long type name> = Option<very long type name>::None;" as long as further uses of x (such as returning it as the value of the enclosing function) clarify its type. However, when a program is during development, you change things here and there, when one variable binding (such as a function definition), which wasn't explicitly typed, appears in at least two places which require this variable to have conflicting types, then almost certainly the error is going to be generated for a line that you as a human see completely disconnected from where the error actually is. Maybe it's in the function definition, maybe it's in one of its uses. And those things can be further obscured by several indirections of intermediate functions with successfully inferred types.
There are a couple of quality of life features missing (most notably is record update syntax), but I really enjoy that the core language has not changed in 25 years.
In fact, my only previous experience with Scala was from hacking on Isabelle/HOL, which is mostly StandardML, but happens to use Scala in the periphery (scripting, UI, etc.)!
...and also a nice display of SML's grammar: https://people.mpi-sws.org/~rossberg/sml.html
[1] https://en.m.wikipedia.org/wiki/ML_(programming_language)
There's also this video presentation, "The History of Standard ML: Ideas, Principles, Culture": https://www.youtube.com/watch?v=NVEgyJCTee4
The "meta language" part refers to MLs original domain of writing tactics for proof assistants, where the "object language" was the language of the programs you were manipulating, and the "meta language" is the language in which you manipulate the programs. This also sort of makes sense when using ML to write a compiler (the "object language" is whatever you're compiling), but of course modern ML goes far beyond just language processing, even if it's still pretty good at it.
For context, I’m web programmer and I’m also learning game dev, can I use SML productively?
Or are there other tasks that I could use SML for?
With some backing SML could be the language of choice for safe and efficient applications.
There is the Rails-inspired web framework SML on Stilts: — https://github.com/j4cbo/stilts — presumably named after its great ergonomics.
And there is the SDL-powered MosGame, specifically for the Moscow ML compiler — https://github.com/Eckankar/MosGame — it comes with these examples: https://github.com/Eckankar/MosGame/tree/master/examples
But really, SML is primarily good for writing compilers.
https://news.ycombinator.com/item?id=15209814
Also the commentor is one of the maintainers of the ReScript compiler, which is essentially being forked from Ocaml.
Mostly I worked on fancy optimisation passes, and a fast gate-level simulator.
Similar to languages like Haskell which emphasise first-class algebraic datatypes (tagged unions) and pattern-matching in a concise but clear syntax, it's good for writing things that manipulate tree-like and symbol-heavy data structures like program syntax trees and circuit graphs, and quickly trying out new ideas with those.
You would probably be better served by F# or Ocaml for a web-oriented ML stack. SML has less of an ecosystem in that area.