Ask HN: How to study programming language theory as a non CS student?
Hi,
I would love to understand programming languages on a more abstract level. What do they have in common and why? Why has language A feature A but not feature B?
I am an EE/Robotics student and program everyday but I feel like am lacking some deeper knowledge about programming languages which holds me back from becoming a better developer.
What course/book can you recommend?
EDIT: I have written quite a bit of code in Python (Pytorch/Tensorflow), do my coding interviews in C++, and also have experience in web dev with JavaScript (NextJS). I am looking for a CS50 like course. I was thinking of going through the "Writing an Interpreter in Go" course. But would rather learn something less implementation oriented.
27 comments
[ 3.2 ms ] story [ 69.5 ms ] threadThere are also millions of pages on things like python vs javascript, react vs angular . Developers have lots of opinions so you shouldn't find it too hard to find out why languages have different features.
Structure and Interpretation of Computer Programs (SICP) - https://web.mit.edu/alexmv/6.037/sicp.pdf
To find out more about the decisions on language features just read material from the language creators and core contributors.
You might also like "Programming Languages: Application and Interpretation":
1st ed: https://web.archive.org/web/20150926000110/http://cs.brown.e...
2nd ed: https://web.archive.org/web/20210121232912/http://cs.brown.e...
Also recommend lurking on http://lambda-the-ultimate.org/ to find material that interests you.
I would start with a low level language like C, then move to a more higher level like Java and finally end with a more "modern" language like Rust or Go.
Attack the Type System first. Do not read PhD research papers, just the practical aspects of it:
- Why is it that integers I am working with are 8-bit (or 16-bit or 32-bit ...)?
- What is "int x = 7;" translated into by the compiler?
- How is basic arithmetic implemented in the hardware? Integers, floating point etc.
- If my system has 16-bit integers, for example, how can I deal with larger numbers than what 16 bits can accommodate? Some SW implementation to hide HW limitations?
Then go on to understand how more complex types are implemented etc.
From there go on to things like Stack Frames and Heaps and Application Binary Interfaces.
From there go on to memory clean up and why we need Garbage Collectors etc.
...
To me, a Programming Language is a set of rules (enforced by a compiler or interpreter) for deterministic bits manipulation. The Type System is the core set of rules around which everything else revolves. Even lack of a Type System in a language is a Type System.
1. Programming Language Pragmatics by Michael Scott.
2. Concepts, Techniques and Models of Computer Programming by Peter Van Roy, Seif Haridi.
I think the information you're looking for would probably come under the umbrella of "Programming Language Design", not "Programming Language Theory" (PLT). Discussions on language design would include topics such as object-oriented vs functional programming, static vs dynamic typing and, importantly, language usability.
However in my experience, PLT is almost entirely concerned with academic research into the properties of highly-advanced type systems. Most of PLT seems to be irrelevant even to the designers of industrial languages, let alone users of them.
Another thing I've found very helpful is to investigate the details behind how existing languages work. It's especially interesting to think about how language flaws are sometimes unavoidable consequences of the underlying design.
For example, you mention familiarity with Python. Dynamically-typed scripting languages are my area of interest, so I have spent time making sense of Python's object model [2], including things like the descriptor protocol. It's then interesting to compare it to Ruby's object model [3], which despite surface similarities actually works in a completely different way.
[0] http://www.craftinginterpreters.com/
[1] https://twitter.com/munificentbob/status/901543375945388032
[2] https://docs.python.org/3/reference/datamodel.html
[3] https://www.youtube.com/watch?v=X2sgQ38UDVY
The Brown PLT group [1], responsible for the Racket programming language in particular, is a notable counterexample. But it's still a shame that I can't give any other counterexamples. (I used to joke that everything PLT but not type theory comes from the Brown PLT. It sounds no longer funny.)
[1] https://cs.brown.edu/research/plt/
If you want fancier designs then look into less mainstream languages (elixir, pony, haskell, swift, rust, kotlin, ocaml, zig, julia, lobster). All of them have some innovations that try to solve common problems faced in (specific) software development or languages.
Generally tradeofs are between speed(runtime, compile), size, correctness and usability.
There are kinda two approaches to programming langs, one from CPU perspective(C) and other from math perspective(Haskell, Lisp, Prolog). There are also pragmatic langs for biulding bigger systems where readability and pragmatism is king (Java, Ada, Go) There's also handling of async/parallel stuff that's not well solved yet AFAIK but most developed is BEAM VM and Haskell/Pony.
To understand CPU perspective I can recommend book "CODE". Other perspecive probably SICP course.
I am average dev so maybe some lang researchers can provide more info.
> In the end ability to solve problem wins
Absolutely true. Languages are tools. They're not religions, they're not rock bands or sports teams, they're just tools. Pick which one works best to get the job done. Not which one is best for "programming in general", whatever that is, but which one is best for the program you're trying to write. That includes ecosystem (library, IDE support, etc.), your own familiarity and that of your coworkers, existing code base that could be re-used, etc. That doesn't always mean "pick the familiar language", but it means that you need to have fairly compelling reason to not do so.
Which, I guess, is to not answer the original question. If you want to study programming language theory or design, go for it. Enjoy! But if you're a working programmer, don't get lost in the theory. In the end, ability to solve problems wins.
https://www.coursera.org/learn/programming-languages https://www.coursera.org/learn/programming-languages-part-b https://www.coursera.org/learn/programming-languages-part-c
The best way to get into programming languages is learning different languages, play with them and write relatively complex applications in them. LISP and C are the most fundamental languages that will give the aha moments. In addition to those, I would learn Haskell and perhaps some object oriented language.