- dozens to hundreds of compiler error lines for a single error, where it's hard to find out what the real problem is (IDEs often point to the wrong line)
- Code is hard to follow. E.g. try to figure out from boost asio source code which code is actually used if if you do a async_read(socket). I personally gave up after the second level of template substitutions, and have only a chance to follow the execution path in the debugger.
- Besides goto definition also other IDE features do not work really well with templates. E.g. no autocompletions for constructors with make_shared.
That's because D's standard library doesn't use templates in the same way as the STL (No iterators, less policies). Also, D has is actually vaguely modern and has proper static reflection, static asserts and static if: Writing template constraints is easy, unlike C++ (even with Concepts/-lite)
Well, let me give you an example that I have seen recently.
There was this function that suppose to convert numeric value to string.
So numeric type was templatized. Then with combination of enable_if and static_asserts there were checks to avoid doubles/floats negative numbers. So whats there left besides unsigned integers?
- dozens to hundreds of compiler error lines for a single error, where it's hard to find out what the real problem is (IDEs often point to the wrong line)
- Code is hard to follow. E.g. try to figure out from boost asio source code which code is actually used if if you do a async_read(socket). I personally gave up after the second level of template substitutions, and have only a chance to follow the execution path in the debugger.
- Besides goto definition also other IDE features do not work really well with templates. E.g. no autocompletions for constructors with make_shared.