Afaics there is no programming language available that has all the following features:
- Typeclasses (Rust's traits) instead of that anti-pattern subclassing. Including trait bounds on polymorphism and trait objects.
- Polymorphism of types and functions.
- GC every where except ability to use borrow checking to track lifetimes of temporary objects to free them without burdening the GC in many cases. And copying some of v8's techniques for improving the robustness of handling temporary objects for those cases that fall through to the GC.
- Asynchronous programming, e.g.
- Thread pools and work stealing.
- Not a gobbledygook clone of Haskell's syntax and philosophy. Otherwise PureScript would be reasonably close to what I want, except lacking #4, #5, #9, and #10.
Those are the features I feel I need to see in order to be confident I am coding to the next mainstream programming language which will eat most of the other languages out there.
Go, Swift, and Rust each have parts of the above. On further reflection, Scala appears to be closest but with many of Java's plus Scala's additional warts (<--- worth listening to 5 - 10 minutes).
- PureScript is lacking #4, #5, #9, and #10. Is it also lacking #8? It obtains something like #4 with functional programming coroutine, but IMO that is more gobbledygook.
- Go is lacking #1, #2, and #7. Is it also lacking #6 and #8?
- Swift is lacking #3, #7, and #9. Is it also lacking #4, #5, and #8? And is LLVM not a robust #6?
- Rust is lacking #3, #4, and #7. Is it also lacking #9? And is LLVM not a robust #6? And it adds total ordering on borrows which in my current understanding (open to change if I'm incorrect on some technical points) I don't agree with.
- Scala is lacking #9. Appears #4 and #5 are only attained via a library such as Akka, so it may add another layer of obtuseness. Afaics Scala sort of has modules but doesn't have all of the features of Crates. Scala's variant of typeclasses are achieved with implicits and objects.
I'm presuming the mainstream wants GC instead of
- the latter burdens the programmer with reasoning about circular references
- there is some reason to doubt whether the latter is more performant than the former (either throughput or memory consumption) in the single-threaded
Rc case and certain the latter is less throughput in the multi-threaded
Arc case. I am presuming GC optimizations cited in this thread, and also that refcounting will not free circular references so it can end up consuming memory that GC would deallocate. I mean to imply they are probably (guesstimated) roughly equivalent performant in the single-threaded case on average for all programs.
- the latter can't become more performant (at least not without changing all the code that is employing it), i.e. there is little improvement we can make. GC can undergo much optimization, research, and tuning between the language's semantics and in many cases without needing to change the code that is employing it.
- the latter can have huge latency pauses as well. GC can be designed to tradeoff throughput to make guarantees about maximum latency pauses.
I'd love to know what other people think. I need to find some forum where I can get feedback on programming languages. I lost access to LtU and I don't think their focus is from the perspective of the actual programmers, i.e. they will give a theoretical bias and not a "what we need for our daily work" bias (and a poignant example). If anyone can suggest an appropriate forum for me, that would be much appreciated.
$ looks incredibly noisy to me.
We know Haskell won't be preferred by many programmers, because it has been around a long time and is still stuck at 0.5% market share.
Edit#2: metrics of language popularity:
I find it noteworthy to compare "IEEE" and "Trending" on only language for mobile, and to see that programmers are forced to trend to C/C++ to get around Java warts, and the only other trend is Swift/Objective C. This indicates to me that there is a hole that remains unfilled in this design space. Programmers aren't satiated with one language on mobile.
Edit#3: I just realized Paul Graham writes some of the same points that have been in my mind:
...designing programming languages is like designing chairs: it's all about dealing with human weaknesses.
Most of us hate to acknowledge this. Designing systems of great mathematical elegance sounds a lot more appealing to most of us than pandering to human weaknesses. And there is a role for mathematical elegance: some kinds of elegance make programs easier to understand. But elegance is not an end in itself.
And when I say languages have to be designed to suit human weaknesses, I don't mean that languages have to be designed for bad programmers. In fact I think you ought to design for the best programmers, but even the best programmers have limitations.
...a lot of the best ones were languages designed for their own authors to use, and a lot of the worst ones were designed for other people to use.
The argument for designing languages for bad programmers is that there are more bad programmers than good programmers. That may be so. But those few good programmers write a disproportionately large percentage of the software.
Give the Programmer as Much Control as Possible.
Many languages (especially the ones designed for other people) have the attitude of a governess: they try to prevent you from doing things that they think aren't good for you. I like the opposite approach: give the programmer as much control as you can.
Aim for Brevity.
Brevity is underestimated and even scorned. But if you look into the hearts of hackers, you'll see that they really love it. How many times have you heard hackers speak fondly of how in, say, APL, they could do amazing things with just a couple lines of code? I think anything that really smart people really love is worth paying attention to.
And it's not only programs that should be short. The manual should be thin as well. A good part of manuals is taken up with clarifications and reservations and warnings and special cases. If you force yourself to shorten the manual, in the best case you do it by fixing the things in the language that required so much explanation.
Speed Comes from Profilers.
Language designers, or at least language implementors, like to write compilers that generate fast code. But I don't think this is what makes languages fast for users. Knuth pointed out long ago that speed only matters in a few critical bottlenecks. And anyone who's tried it knows that you can't guess where these bottlenecks are. Profilers are the answer.
Language designers are solving the wrong problem. Users don't need benchmarks to run fast. What they need is a language that can show them what parts of their own programs need to be rewritten. That's where speed comes from in practice. So maybe it would be a net win if language implementors took half the time they would have spent doing compiler optimizations and spent it writing a good profiler instead.
Edit#4: I'd like to correct the tradeoffs of programming language paradigms. I think typeclasses (TC) subsume OOP+AOP providing the benefits of both without their drawbacks, especially when my proposal for a complete solution to the Expression Problem is included:
....★...............✗.............ⁿ/ₐ.......ⁿ/ₐ......ⁿ/ₐ...Scalability (e.g. parallelism, concurrency)
....★...............✗.............✗........✗......✓...Verifiability (algorithmic reasoning)
So this is why I prefer a design philosophy of encapsulation of interfaces with FP+TC where possible, yet retaining imperative where necessary. I am currently thinking best to throw OOP+AOP and even subtyping into the trash can.