The trouble with special cases is that they come in two very different flavours. Some are essential complexity, inevitable consequences of the problem you're trying to model. Others are accidental complexity, artifacts of the development process, often things that came along when requirements changed after the initial design was set and didn't fit in neatly but didn't justify reworking the whole thing either.
You can never get rid of the essential complexity, but with the wisdom of hindsight you can often produce new design that integrates the accidental special cases into a coherent whole. I've seen modules cut to 1/3 their former size and various "can't fix" bugs eliminated as a consequence.
That plus the lack of understanding of why the code is complicated. Corner cases and exceptions are a huge PITA.