What could even be in common between Haskell and Rust? Well, they are the most advanced languages of its time, the most controversial and the most discussed.
Most importantly - both languages are have a proper type-classes/traits based standard libraries, where the type-classes/traits define major modern mathematical notions, which can be traced to the modern set-theoretic math and related notions. This is what makes the actual difference with other crap like PHP.
While Haskell has been researched (and developed) by the actual top people in the field (Turner, Bird, Wadler, Hudak, SPJ) – all of them had a serious mathematical background – the Rust community is diverse but trying to incorporate all the nice things the previous generations have discovered.
This is not just about stdlib, of course (however important that is by itself). The major innovation was in restricting possible behaviors of variables and references to them in a systematic, formalized way. This is the only real major innovation in last 20 years or so.
Restricting the behavior to avoid “paradoxes” (or just errors) is a Universal pattern (no jokes here). It is exactly the same process as how Evolution selects just a very few stable molecular patterns (proteins) and arrangements (cell membranes). We could easily call this a restriction on all possible molecular arrangements.
The first such restriction has been discovered within the Set Theory, which has been proved to be way too general. One has to specify the particular Set one works with, so expressions (set comprehension) would not lose its meaning. This is essentially “typing” (or a rudimentary type-discipline) within a mathematical formalism.
Another such instance was restricting the behavior of, again, way too general the Lambda Calculus (another mathematical formalism) by introducing simple typing (otherwise eveything could be applied to everything, which would eventually yield bullshit).
And Barbra Liskov noticed that most of the mathematical :“structures” have been defined by a subset of “objects” defined by a set of all possible (and meaningful) operations on them So should be our Abstract Data Types.
The authors of Haskell (mathematicians) have chosen a particular system of pure logic as the basis of the language, so everything is pure and immutable as in math itself. This system of logic is defined as a small extension of (augmented) Simply Typed (restricted) Lambda Calculus. Every Haskell expression will be simplified to an intermediate representation which is just that – terms of a particular system of logic. Haskell has been discovered, not invented.
Again, this is not an arbitrary decisions, this is a universal pattern – too general (and too abstract) is unusable. In a theory (at least) Evolution “selects” (by trial and error) a stable subset of all possible arrangements (which does not break easily). Similarly, mathematicians and programmers discover what Evolution has “selected” earlier and the universal patters, such as “putting together” (addition), sequences and actually existing symmetries.
So, what Rust
has to do with all this? Well, it does a lot of things “just right” (beginning with restrictions on the behavior of references) and the community, however diverse, has emphasis on doing thing right. All the emergent properties of the language magically appear (actually follow from the small set of right decisions based on the fundamental notions of mathematics).
The restriction of having either at most one exclusive mutable reference or an arbitrary number of immutable references is what yielded all (well, most of) the emergent properties memed as “safety”.
In functional languages references are explicit closures (a proper ADT) and are being explicitly passed around as parameters to functions, so this property (at most one mutable reference at all) is implicit. All the bindings are implicit immutable symbolic references to values.
Lifetimes associated with every variable and then lifted into the type-system was another discovery. In functional languages there is not time, so all expressions, including bindings (their “lifetimes”) are eternal (being a pure logic is not a joke).
Rust is trying to become an expression-oriented language as much as possible (including pattern-matching on data bindings), while the best functional languages have it “naturally” – everything is an expression, which is reducible (denotes) a value (in a so-called “normal form”). Thus the “data constructor” can be viewed (semantically) as “tags” to values, and be matched against. Rust is not so uniform and universal, of course, but it is at least something.
Even with this quick overview, Rust
is by far the most advanced imperative language (don’t even think to embarrass oneself by labeling it as sort of functional – only Chuds do this), which borrows all the nice things from the Haskell and ML (as much as possible).
Use of Algebraic data types (sum-types) through the standard library is another nice “borrowing”. It makes everything more uniform and “just right” (an Option type is a proper abstraction which captured the notion of possibly Nothing as in $x - x $).
I could go on, further into other particulars, but I think this writing is already good-enough to show that Rust is sort of an “Imperative Haskell” at many levels. It could be way better polished if designed by a small group of renowned, passionate and principle-guided mathematicians, but the time of small groups (and garages) has already gone. So, Rust is also PHP (inevitably).