Mapping Languages to Paradigms
Question: I recently read Eric Steven Raymond's article "How To Become A Hacker" and I
like his suggestion of learning 5 key languages (he suggests Python, C/C++,
Lisp, Java, and Perl) as a way of covering the main programming paradigms in
use today.

His advice is that it's not so important which specific languages a programmer
knows. It's more important to know different approaches to programming, for
two reasons.

The first reason is that it makes it trivial to pick up a new language, once
you know the general approach to the way it solves problems.

The second reason is that there is no one best language - they all have trade-
offs. It would be best to know what type of language to pick given a specific
type of problem. This is what I'm most interested in, but I'm having a problem
really distinguishing between the 5 languages he suggests. There seems to be a
lot of overlap.

So my specific question is, given these 5 languages, what is their intended
programming paradigm, and give one example of the type of problem it would be
best suited for.

An example answer (and I'm not sure this answer is correct):

    
    
    Perl
    - mainly a functional language
    - great for quick text substitutions in multiple files from the command line.
    

I found a few other similar questions posted, but I'd like to know about these
5 languages in particular. I'm just looking for a starting point, nothing too
detailed. Thanks in advance!


Answer: I think you're approaching it wrong. As esr himself says, it's not the
_language_ that matters, it's the _paradigm_. So when you say that

>   1. Perl is a functional language
>   2. It's great for quick text substitutions in multiple files from the
> command line
>

you are missing one of the main points of a functional language which is that
they are great for building large systems using a bottom up approach: solve a
bunch of (well chosen) small problems with well designed functions until we
have a complete system. We cut down on code duplication by identifying what
algorithms that we are using have in common and using higher order functions
to encapsulate their commonality. We minimize (overt) branching behavior by
using higher order functions to cook up just the function that we need for a
given situation.

Likewise, I could say that

>   1. Java is mainly an OOP language
>   2. It's good for writing large, robust systems,
>

but that misses the point that OOP languages are about modeling concepts from
the problem domain in code so that we are left with a clear way to
imperatively solve the problem at hand. We cut down on code duplication by
identifying what the relevant concepts have in common and encapsulating the
code that deals with those commonalities in a class that describes it. We
minimize (overt) branching behavior by providing different subclasses of an
abstraction with appropriately different behavior.

On the whole, the basic point of programming languages and their associated
paradigms is

  * to allow you to not think about anything that doesn't affect the quality of the resulting program. If that wasn't a (largely) desirable thing, then we would all be writing machine code. 

  * This is accomplished by (among other things) providing a set of tools for _building abstractions_. 

Shop around and pick one that you like and get good at. Just make sure that
you learn when the other ones allow for a better solution (this will probably
mean getting good at them eventually too ;). I think that you can mainly take
"good solution" to mean, "clear mapping of **code** to **ideas** ". (modulo
concerns about efficiency that would force you (provide an excuse?) to write
in a language like C)

