2. Doing NAND to Tetris the first time. It taught me not only how computers work, but how powerful recursive layers of abstraction can be. I had absolutely no idea how my system looked on RTL, but I was still able to build it.
3. Also Lisp. I wish Nand to Tetris had picked something more lisp like in the second half to show how simple and powerful it is.
4. When I'm just coding something- alternating writing and testing - is much quicker than writing a bunch and then debugging it. For bigger projects, setting up CI/CD early can similarly save headaches.
5. The functional big three (map, filter, reduce), but for me even more so closures. I had gotten stuck trying to hardcode coefficients for a polynomial until I noticed I'd end up with a lot of duplicate code, which was what I was trying to avoid with FP in the first place. Then I realized I could just put the polynomial function itself in a closure and call it with the coefficients I wanted, when I wanted.