Testing, plain and simple. I sort of had to be dragged to it, but now I'm addicted. And it turns out that it has some great features that will, over time, make you a better programmer.
First, you discover that if something is hard to test, it's a code smell. Doesn't mean it's wrong, but there's a good chance that when you're struggling to test all combinations of those five arguments to a function, you're doing too much in that function.
Second, "fear-driven development" is a thing of the past. Many times developers find themselves afraid to touch a hairy section of code because it's grown over time and has become unmaintainable. Having fear back you into a technical corner is never pleasant. With good test coverage, it's much easier and safer to dive in and make those changes. "Fear-driven development" goes away.
Third, your overall designs improve. As with the first point, not only do you discover that discrete bits of code become more maintainable, you find yourself wrapping global variables in well-guarded method calls to ensure that you can test them easier. Later, when something else break this "global", it becomes trivial to add logging to find out what does it. Further, you find that your code starts decomposing into different sections that are easier to test, but this also tends to be better-designed code.
Fourth, you'll be more productive. The studies I've read tend to show that initial productivity drops between 10% to 30% while testing, but long-term productivity increases because you have fewer bugs. When you implement a new feature, you can code as fast as you want, safe in the knowledge that a strong test suite will catch many errors. Also, when bugs do arise, good test suites generally help you pinpoint their source much faster.
Fifth, you can work as a team better with tests. When Joe and Sally both check in code which passes all tests, often the tests fail when the code is merged. This can be a very subtle issue when working on separate areas of the code. I confess that sometimes I hack together code quickly just to explore an idea, but when I'm working with others, I wouldn't dream of it. Tests will save me again and again.
Sixth, you know where bugs are before you find them. This sounds weird, but over the years, I've discovered that when I run test coverage code, those areas of my code which aren't tested are almost always those areas of my code where serious bugs/design flaws are working. It happens to me again and again. Look for areas where your test coverage falls short and you'll find bugs. Even if you don't see them, write tests for them and those bugs will start crawling out of the woodwork.
Testing is far and away the best tool I've found for making me a better programmer who turns out more code, to deadline, with fewer bugs.