4 ms·
> it's always tempting to think that we can create a perfect language that would be the best in all situations but we can't Why can't we design a language that
by Pyxl101 11y ago
> it's always tempting to think that we can create a perfect language that would be the best in all situations but we can't
Why can't we design a language that would be the best in all situations? I see no reason necessarily to believe that's true, though I recognize that it has not yet been done.
It may be impossible to create a car that is also an excellent submarine and a great airplane, but software is not subject to the same kind of physical limitations. I see no reason in principle why a perfect language could not be malleable enough to accommodate all situations optimally. I realize that my writing here is not a convincing assertion that such a language can exist. I recognize that. I'm just saying that there doesn't seem to be strong evidence that it can't exist or that we should give up trying to design it.
A person who wishes to argue that the perfect language can't exist should perhaps give an example of two different problems that cannot be solved well by any single known language, and that can be solved much better by two programs in two different languages. I would like to dissect that example and see if we can indeed find such examples of sets of problems that cannot be solved well by one language. If we cannot find such problem sets, then that may suggest that we can indeed "unify" programming under one perfect language, by tweaking its syntax and semantics appropriately.
- kibwen 11y agoMy go-to example is shell scripting. In a shell language, you really, really don't want to be forced to quote strings, and you typically also don't want to have to explicitly parenthesize command invocations. Take a typical shell command: rm -rf foobar You may not think about it much, but these are all just strings. Go ahead and type this into your shell, it will have the same effect: "rm" "-rf" "foobar" Now imagine how utterly annoying it would be to use your shell if you were forced to quote every string you ever typed. Even worse, here's how the above would look in Python-esque syntax: call(["rm", "-rf", "foobar"]) Sysadmins would riot in the streets. Most languages that are explicitly designed for scripting offer this feature: TCL and Perl both allow unquoted strings (Perl with `use strict` places some limits on them), and I believe Ruby has some way of enabling this as well with `method_missing`. But it's important to note that this behavior is almost never what you want for programming in most other domains, which is why most other languages (particularly non-dynamic ones) don't even offer anything resembling this feature. And of course, you can have a single language with both! You could have it controlled by a flag or something. Super great. But this is just the tip of the iceberg. When you import a namespace in your language, are all its identifiers automatically brought into your local scope, or must you import them one-by-one? For fast-and-loose tasks you want the former, for long-term maintainability you want the latter. But we could have a switch for this too. Still great. Now, when you `x = new Blah()`, is that Blah on the stack or the heap? This has enormous implications for both semantics and performance, and if you truly want an all-purpose language then heuristics like escape analysis won't save you, you need to be able to control this. On and on we go, until your language has a million little switches that may interact with each other in surprising ways, because different programming tasks actually do have different needs, and although your language may ultimately be capable of fulfilling all these tasks, in practice it will be considered a dozen different languages trying to coexist in the same compiler (with no consensus on where to draw the lines that demarcate each). Meanwhile, people who want to Get Things Done will opt not to wrestle with your Swiss-army language and will instead favor more limited languages that fulfill the needs of their specific tasks, because the vast majority of people are not writing client-side code in the morning and device drivers in the afternoon. Now, there does exist a scenario where One Language To Rule Them All can dominate: when the market for programming languages is very small. If the market is small, then demand for domain-specific languages is less. Or rather, the value of differentiation is less, because your differentiated language will have a small share of a small market, and will be unable to thrive. But in a large market, even a small share is enough to subsist on. In reality Go and Rust likely have 1/1000th the number of programmers as Java and C++, but even 1/1000th of tens of millions is more than enough to support large and thriving communities. So ultimately it's not that it's impossible to make a language that's great for all tasks (though it would still be difficult), it's that there's not enough demand for one, and if you believe that the cohort of programmers is growing then demand for one will only continue to decrease.
- rntz 11y agoThe best possible a language can be for a given situation is that the empty program solves the problem you're trying to solve. Obviously, in no language can the empty program solve all problems. QED, there is no language that is optimal in all situations. If you want a more useful answer, you should define what you mean by "best in all situations".
- stefs 11y agomy guess is this is because of hardware limitations and the absence of the mythical sufficient smart compiler. in the one language you write to appease the hardware, which makes it fast. the other language appeases the programmer, which makes it productive and safe. the two goals are irreconcilable as long as the processor and the (the mind of the) programmer work in a different way. the simplest example i can think of are array boundary checks. as long as memory is finite you have to manage allocated ram. is it possible to know beforehand if an out of bounds access will happen? no; not without certain restrictions. i'm pretty sure at the core there's some undecidability/halting state problem. or the CAP theorem; consistency, availability, partition tolerance. it's impossible to provide all three: so you might have two languages that solve two different parts of CAP, but leave the third one to the programmer. depending on the problem at hand one language might fit you better than the other.
- jerf 11y agoTacking on another example to kibwen, while a language can be multiparadigm, where one paradigm is in conflict with another, one of them must win. Further, the language generally must choose some default values (as in philosophical values, not variable values) which will become ingrained into the core library and shape the entire rest of the ecosystem. If you agree in the utility of multiple paradigms, then there can not be one language that does them all. If you're going to be a logic language like prolog you're going to have to privilege syntax and semantics to make that work. If you're going to be a query language like SQL, you're going to have to privilege syntax and semantics to make that work. If you agree with the utility of multiple different language values, you can't have one language that does them all equally well. If your language permits mutability, it will work its way throughout all the standard language code and all the library code, and once you have that you basically can't write immutable programs anymore. If your language is based on immutability, all the library code will be based on that and it will be difficult to drop that last "log n" factor that immutable code often imposes on your runtime, plus some of the other characteristics it has that can cause trouble with things like cache coherency. In both cases you can layer something else on top of the core language that may recover the functionality, but the second layer addition will always come with a lot of caveats, sharp edges, and poor interaction with the rest of the standard library. There are many of these dimensions where a language must pick one place on the spectrum, and even if you pick "in the middle" that never ends up meaning "the best of both worlds with none of the drawbacks!"... it's just a point in the middle. "A person who wishes to argue that the perfect language can't exist should perhaps give an example of two different problems that cannot be solved well by any single known language" I want high reliability code that I would literally trust my life to, that can be verified both by the compiler and by any other arbitrary external tool that may assert proofs of things that may be desirable, such as "it never crashes as long as the hardware operates correctly" and "there is never a null pointer exception". I had a cool idea last night, and I want a website up that implements it by next week. You will never be able to bridge the gap between someone who wants to slap something together quickly and someone who wants to write provably correct code. I don't think we're at the Pareto optimality frontier and that there is still some improvements to be made in general, but even after those improvements, the two ends of that spectrum will forever be separated by a huge gulf, and no one language could possibly straddle it. You can't practically script in Idris or Coq and you can't practically write provably-correct code in a dynamic scripting language. In either case, by the time you made the changes that might permit it, you would no longer have the original language, i.e., TypeScript may take many steps towards letting you write reliable Javascript, but it's no longer the same language anymore, it's a new one with a JS compile target.
- grok2 11y agoI think what you will end up with then is Java? It works everywhere and has features for everything and has support for almost all programming language concepts/paradigms or comes very close. We probably just need to fine-tune/minimize Java to arrive at the final perfect language :-).