I would like to learn programming but haven't been able to get started. Advice appreciated, both high-level (you should try learing language X) and low level (you can find a program that will run language X here), the latter has been a particular problem for me, I don't really know how this sort of thing works.
I am currently studying maths and physics, and I have a particular talent for the former, so I would probably do well with a language that plays to that strength. My only actual experience with programming was when my father let me play around with Jython a bit when I was about 13, I had some fun calculating prime numbers and approximating pi but never got any farther.
Thanks in advance for all suggestions.
In that case I'd second the Python recommendation, and add Ruby, as mainstream choices; for a somewhat more exotic choice see Haskell which I've found excellent for Project Euler type problems.
Both Python and Ruby are interpreted ("scripting") languages, which allows you to focus on the programming and not worry overmuch about ancillary matters such as compiling and linking.
Haskell is compiled but also has an interpreter; it's a functional language, a programming paradigm which is perhaps closer to the mathematician's way of looking at things. When I was playing with Project Euler it was as an exercise to learn Haskell, and I really liked how the language and the problems meshed together.
For instance you'd start on the first problem by defining a predicate, a boolean-valued function, determining divisibility. (You can type almost everything in what follows into the Haskell interpreter if you want to follow along.)
In the Haskell interpreter ghci this is done by using the keyword let, followed by the function name, followed by formal parameters, followed by "=", followed by the function definition:
If you've done prime numbers already this should be somewhat familiar: "mod" is the modulo operator. (There is also a Haskell notation to express this in the more familiar infix form; you can look that up later.)
In Haskell as in math you can leverage your definitions in further definitions, so we can say, naming our predicate "divisible by 3 or 5" fizbuz in honor of a common programmer's meme:
Where Haskell and other functional languages shine is that functions can be used as parameters to other functions. For instance, you can pass a predicate as a parameter to a primitive function named "filter", which takes a predicate and a list, and returns only items in the list matching the predicate:
should return [3,5]. Haskell has plenty of primitive functions which operates on lists - you can build lists, filter lists, but also for instance sum over lists:
will return 16. We can also use this syntax to define lists from more compact ranges: [1..10] means the integers between 1 and 10.
Another area where Haskell feels like home to a mathematician is that you can compose functions, and reason formally on the types of functions and their arguments. For instance the type of our function "filter" is this:
(Don't type this in at the ghci prompt. You rarely need to enter these types by hand, because Haskell figures them out for you. But you sometimes will have to, in order to lift some ambiguity for instance.)
We parse this as "a filter is a function which takes as arguments a function mapping integers to booleans, and a list of integers, and returns a list of integers". The type of this function:
is therefore [Integer] -> [Integer], that its, it takes a list and returns a list. Since the "sum" function takes a list and returns an integer, we can compose sum and this function (but, note well, not the other way around)
or equivalently
The latter being "more expressive" and therefore preferable because it shows more clearly how our computation is arranged: we sum over a list filtered by a particular predicate.
Now finding the solution to problem 1 is as simple as entering:
for the test case, and solving the real problem is left as an exercise for the reader.
What's nice about this is that several early problems also take the form of "sum over a filtered list of integers in a certain range". All you have to do to make these problems dead easy to solve is turn the predicate by which the range is filtered into a parameter to sumFilteredList. Then each such problem reduces to a particular case of the general procedure of filtered summing which you have already solved.
sum [ i | i <- [1..999], mod i 3 == 0 || mod i 5 == 0 ]
:)
Haskell is amazing for Project Euler. Lots of these problems are one liners in Haskell. Actually I think Project Euler is excellent for learning Haskell tricks specifically, even if you know how to program already. For certain types of tasks, Haskell is an immense force multiplier.
Of course the difficulty with Haskell is that it is both functional and lazy, which means it explicitly hides the causal order of operations from you for other gains (expressiveness, parallelism, etc.) The problem ... (read more)