The thing that improved my coding was actually maintaining my own codebase for a few years (4.5 years in the same job working on a system that I wrote from scratch). That way you see which of your decisions worked and which ones were crap. When you need to revisit your own code 6 months later and can't understand it, that's no one else's fault but your own.
Even then I think you have to be able to look at your own code critically and want to make it better. The current tech lead in my company churns out a lot of code quickly, but doesn't take constructive criticism of it at all well. It's not easy code for other people to jump into and there are no docs or tests. He thinks it's close to perfect. I don't
This is an issue I've seen with programmers that hop around companies every year or two - they rarely get to see how their software choices play out in the long term and so never really internalize what works and what doesn't. Same issue to some extent with people who keep hopping around languages/frameworks - if you only have experience writing projects from scratch you'll never really understand what works and what doesn't from a long term maintenance perspective.
Even then I think you have to be able to look at your own code critically and want to make it better. The current tech lead in my company churns out a lot of code quickly, but doesn't take constructive criticism of it at all well. It's not easy code for other people to jump into and there are no docs or tests. He thinks it's close to perfect. I don't