The idea of a LanguageComparisonFramework
, seemed obvious. Lots of pages debate language issues without seemingly any kind of consistency or systematization. language qualities are therefore in the eyes of the beholder. For the Python aficionado, the EconomyOfExecution
is obviously unimportant, for the SmugLispWeenies EconomyOfExpression
cannot trump the regularity of structuring everything around the EssExpressions
So let's enumerate them, and maybe dedicate them a page on their own. I start with Cardelli's framework from his initial BadEngineeringPropertiesOfOoLanguages
. And I took the liberty of refining some and adding some.
- EconomyOfExecution. How fast does a program run? How well does the runtime semantics of the language integrates in more complex architecture?
- EconomyOfCompilation?. How long does it take to go from sources to executables?
- EconomyOfSmallScaleDevelopment?. How hard must an individual programmer work?
- EconomyOfLargeScaleDevelopment?. How hard must a team of programmers work?
- EconomyOfLanguageFeatures?. How hard is it to learn or use a programming language?
- LanguageEcoSystem?. How healthy is the economical eco-system developed around a programming language? What are its notable performances/failures?
- EconomyOfLanguageCommunity?. How likely is it that your language questions will be answered? How well is the language maintained?
Some of them need future refinements. EconomyOfSmallScaleDevelopment?
are kind of fuzzy. Is on the other hand a trait like EconomyOfCompilation?
still relevant in the days of Ghz, Gb development workstations? How about EconomyOfExecution
Since in my humble opinion EconomyOfLargeScaleDevelopment?
are somewhat fuzzy and subjective, we should look for more modular units that drive the economies both at large scale and smaller scale.
Perhaps, we might also add...
- LanguageLegibility? (which can complement or conflict with EconomyOfExpression)
With regards to the above maybe we can gather some realistic LanguageTestCase
s. Some tentative have already been provided here on wiki. One is OddWordProblem
. However that problem is to some degree somewhat trivial.
An ongoing year after year LanguageTestCase
is provided within IcfpProgrammingContest
Another very interesting example I came across recently is EnumeratingRegularLanguages
. And it is very interesting because it shuttered some of the prejudices I had against HaskellLanguage
and my over-confidence that for any such task SchemeLanguage
was the way to go for me (haskell is vastly more complicated and with a steep learning curve, and subject to loss of memory while Scheme seems to be like learning to swim or learning to bicycle, you never forget that). -- CostinCozianu
I had run into a similar problem - noticing how most features of a language were aimed at common goals. In evaluating a language, remember that one shouldn't evaluate the strict text representation of the language, but the actual tools a developer uses. If a language is primarily handled through code generators, it is those code generators that should be assessed.
Very often when faced with a problem in any given language, you'll end up thinking "I can do that, but it will break OnceAndOnlyOnce
", "I can do that, but it's hideous", or "I can do that, but it breaks type safety", or even worse, YouCantGetThereFromHere
. As such, I thought I'd try and describe the yardsticks to measure a language by to see how they compare.
The core goals of language/development-platform design should be to maximize these following attributes:
1) Ability to maintain OnceAndOnlyOnce
for as many concepts as possible. This is more than functions and subclassing - consider code that converts an enum into a string - in C++ this requires having an array full of strings that contain the same information that you already wrote in the enum declaration.
2) Learnability - code should be as legible and self-documenting as possible. How smart, experienced, and well-read must a programmer be to read or write functionality? Achieving this goal may require making the language simpler than would be preferable, or adopting language conventions from the ever-popular AlgolFamily
languages. Libraries and language concepts are useless if the coder doesn't know about them.
3) Evaluatable - as much of the validity of the program as possible should be determinable at compile-time. Type Safety, DesignByContract
, and FunctionalProgramming
all contribute to this.
4) Task Implementability - the language (or libraries) should maximize the functionality available to the user. Regardless of how they say it, the user should be able to do as much as possible in the language. Java, for example, fails to provide facilities for speed-critical non-garbage-collected code. Python has no way to execute a module with restricted permissions. Some web server languages provide no way to distribute their app as a binary. Code generators often do not allow you to edit definitions after the code has been generated and modified. Many languages will have hacks to provide previously unavailable functionality, these hacks will destroy the legibility and evaluatability of the code. "can you do that in X?"
5) Development Speed - the language must allow the user to solve their problems as quickly as possible. This may involve providing a laundry list of libraries to solve common problems, or simply that some concepts are natively expressed in the language in a way that makes these tasks easy to implement. Closely related to Learnability, except that in many languages, a task will take a long time even after you know how to do it. "how long will it take to do that in X?"
6) Safety - how catastrophic, detectable, and likely is programmer error? This is closely related (and nearly redundant) to Evaluatable.
7) Reusability - you should be able to reuse your code as easily as possible.
- Ability to GroupRelatedInformation - this isn't really an issue on its own, but contributes heavily to the legibility and reusability of a language. C++ provides a problematic example - initializers for members must be located in the constructor, not on the member. The problem with GroupRelatedInformation is that these initializers are related to both the member and the constructor.
I've tried to make this list as direct as possible. The exercise is to think of a language, think of its flaws (why you don't use it), and consider which of these attributes it fails to properly satisfy. For example, most AlgolFamily
users would contend that LispLanguage
fails abysmally on (2) and (5), due to the bizarre (oversimplified?) syntax and standard libraries that simply can't compare to the modern behemoths of DotNet
and the like. On the other hand, the whole Lisp family whups all its opponents at OnceAndOnlyOnce
and some forms of Evaluatability. The perfect language would be one that excels at all 8 attributes for any given task.
But not necessarily. This is not the intent of the page. Having a coherent and relevant LanguageComparisonFramework
together with some objective analyses done over various languages in the spirit of Cardelli's famous BadEngineeringPropertiesOfOoLanguages
, can be a substantial help to software engineers, both experienced and novices. The very idea is to avoid LanguagePissingMatch