top | item 20468252

(no title)

gitrebase | 6 years ago

I like that Python is quite close to my raw thoughts for simple problems. So writing an algorithm in Python almost feels like writing pseudocode. Heck, these days given an option between writing pseudocode and writing Python code, I choose Python for simple problems.

Is there a similar programming language that makes mathematicians feel at home? Something that makes them feel that they would rather write their implementation in that language itself instead of writing it with math notation on paper first?

discuss

order

mruts|6 years ago

I’ve always been in the weak Sapir-Whorf hypothesis camp that your tools of expression influence and (sometimes) define your thoughts. A great example is the idea of matrices in math. Matrices don’t allow you to represent anything that a system of equations can’t. But it turns out that they are a very helpful tool and let you abstract over the problem space, much in the same way that higher order functions do.

It’s exactly like Paul Graham says, you might think that Python is just allowing you to write executable pseudo-code, but the interaction isn’t so simple.

I’ve programmed a lot of Python and when I first started out, I felt like it was very frictionless, like you said. An easy way to put down thoughts. But as I learned more about functional programming and type theory, I realized that Python is inadequate and operates a top low level. i.e it feels like there’s so much friction there.

I have used a variety of languages professionally (Scala, Haskell, OCaml, Racket, C, and Python mostly) and they all fall short (some more than others) on what I feel like I should be able to express. But if I had to chose, I would probably say OCaml or Racket come the closest to my thoughts, depending on the problem.

Anyway, my point is that it’s not obvious how your tools affect the level and abstraction of your thoughts. It’s almost always a bi-directional relationship, and therefore, choosing (or making) the right tool and method of abstraction is very important. See Beating the Averages[1]. PG talks about the a hypothetical language called Blub. Blub isn’t the best, but it’s not the worst either. If there was a platonic form of Blub, it would most definitely be Python.

[1]http://www.paulgraham.com/avg.html

gitrebase|6 years ago

Can you describe some attributes of Ocaml and Racket that make them good contenders for expressing thoughts of mind?

Also is it Racket specifically that makes it a good contender or is it the fact that it is a Lisp that makes it a good contender? Would any other Lisp like Scheme or Clojure or Common Lisp be equally good?

grovehaw|6 years ago

Some people feel at home with APL (A Programming Language) or its descendants. It was first developed by Ken Iverson as a notation to be used on paper for communicating procedures and algorithms. It was the subject of a book published in 1962, then became a programming language running on IBM mainframes in 1966.

The following line of code produces all the prime numbers below the value R.

  (~T∊T∘.×T)/T←1↓⍳R
More history and a full explanation of this code can be found at https://www.computerhistory.org/atchm/the-apl-programming-la...

kragen|6 years ago

A fairly precise raw Python translation for the interested:

    T = range(1, R)[1:]                       # T←1↓ιR
    u = [[t*u for u in T] for t in T]         # T∘.×T
    v = [t for ei, t in
          zip([any(t in ui for ui in u) for t in T], T)
         if not ei]                           # (~T∈u)/T
As the standard poem on the subject by Dave Touretzky and Don Libes says:

    I wrote some hacks in APL,
    each on a single line.
    They're mutually recursive,
    and run in n-squared time!
In this case, of course, it runs in R-cubed time, not n-squared time. There's a perhaps more common, but slightly longer, APL one-liner for finding primes that does run in O(R²) time instead; from https://aplwiki.com/SieveOfEratosthenes †:

   (2=+⌿0=(⍳X)∘.|⍳X)/⍳X
Or, eliminating the inessential variations from the above version:

   (2=+⌿0=T∘.|T)/T←⍳R
If you want APL and are stuck with Python, you can probably get most of the APL you want in Numpy. A slightly looser translation of the first algorithm into Numpy:

    import numpy

    T = numpy.arange(2, R)
    print T[~numpy.equal.outer(T, numpy.multiply.outer(T, T)
                               ).any(axis=1).any(axis=1)]
Recent versions of Numpy have numpy.isin, which works like APL ∈, which would save you the .outer.any.any nonsense.

A much more compelling demonstration of APL is, in my mind, the interactive development process leading up the the one-liner Game of Life in this livecoding video: https://www.youtube.com/watch?v=a9xAKttWgP4

† This is not the Sieve of Eratosthenes, despite the article title; the Sieve is an immensely more efficient algorithm than trial division, producing the same results in near-linear time.

heinrichhartman|6 years ago

> Is there a similar programming language that makes mathematicians feel at home?

The problem is not writing stuff down. The problem is reasoning about what you have written down. With popular languages it's really hard, to say what a line of code does. It depends on so many things (global state, scoping, local state), that you have to spell out. Google "Semantics of Programming Languages" to get an idea, what's involved with formally reasoning about code.

To have a chance to do manipulations by hand, you have to give up, at least:

- Mutable State - Side-effects (I/O)

(pure) Scheme and Haskell come into mind as contenders.

n4r9|6 years ago

Hard to imagine that a programming language could ever be as flexible as mathematical writing, but the more extensible, abstractable, and I suppose functional it is the better.