Thanks - I've been starting to work through this book. I see you are in programming / software engineering - would you say that working through it helped you in your engineering skills (not necessarily day-day, but perhaps your ability to reason about problems)?
Well... it's been a long journey. I'd say that working through math in general, going both wider and deeper, does indeed help with reasoning and being able to reach for theory whenever necessary. Combinatorics, elementary number theory and probability are especially useful. Graph theory as well.
CS is quite math-intensive on its own but it kind of assumes a certain level of math maturity.
Of recent gems: Elementary Number Theory by Underwood Dudley is easy to like. You can really see how it was written with an active reader in mind, with a good and doable set of inline excercises, key problems and additional problems. The material covers all the basics and doesn't try to be original, which is good for self-study.
Instead of listing other books I would suggest the following learning scheme of a programmer trying to deepen their math:
1. No need to go beyond basics. Any uni-level introductory math course is already more advanced than 99.99% uses you might have.
2. Know your basics well. Get 2-3 classic books. Work through the one you like most, but still read through the rest.
3. Practical book size limit - 200-250 pages. Math material is hard, 200 pages of good math is months and months and months and mo...
I worked through it after uni years, and after working for a few years. It changed my perspective on proofs and math completely!
It showed how the language of logic combined set theory form a very small and comprehensible foundation for most of math.
After reading it and a few introductory-level books on number theory, calculus and combinatorics, most of CS proofs started feeling... cute.
Did I say I love "How to prove it"?