There are multiple factors that contribute, but here's a few that I haven't (to the best of my recollection) seen mentioned so far: tooling (crucial), "do the simplest thing that could possibly work" attitude brought about by (lack of) a built-in collections library and simple syntax, and lack of rapidly changing requirements during development.

Tools for C are powerful, mature, and available on near every platform. Every single C programmer that I know uses multiple memory debuggers, for example: e.g., valgrind for leak checks and more on smaller code segments, LLVM address sanitizer on unit test runs, jemalloc or tcmalloc/google-perftools, and more.

"Do the simplest thing that could possibly work" is somewhat close to the author's point: simply put, while there are widely used cross-platform hash tables in C, it takes more effort to use one; hence, they aren't used e.g., when N is known to be 100 (or if maximum size is bound, there's likewise no pressure to use the built in hash table/red-black tree and one can use perfect hashing instead...). In another big distinction I see between code I wrote in C vs. higher-level languages is that one can simply use a stack allocated variable length array -- or (if random access doesn't happen) a linked list in place of a heap allocated resizable array.

These exammples, I think demonstrated how C discourages you from interpreting "the simplest thing that could possible work" as "the thing that is fastest to code"; that's not to say development speed is not an issue -- it's a _huge_ issue! -- but it often leads to code where the unneeded complexity (such as using a red-black tree or a skip list instead of a sorted stack allocated array!) is hidden from the programmer but is nonetheless present.

Onto the last point, I agree sentiment expressed by others questions the premise. I think the examples of C programmers where we explicitly know of something as being a C program are heavily biased towards well known and open source software; open source software, language runtimes, operating systems, browsers (usually in a clean and limited subset of C++ like, e.g., Chromium and likely Firefox as well -- I only mention Chromium as I've re-used base libraries from its codebase), and so on. We don't, however, think of parking meters, vending machines, and many other usually embedded (but not life critical) systems that -- unlike open source systems software -- are built from unclear, confused, and ever changing business requirements ("well, this city introduced a new red-zone, so now we have to make sure to charge extra 0.33 cents between hours 8 and 13 except on all Holidays, but not July 4th").

Yet when people bring up Java, it's easy to forget about gmail or Minecraft, but instead to think of the insurance claim management system that you had to use after your rental car got rear-ended near 4th and Harrison, that crashes with a user-visible stack trace when you click the wrong button and (even in 2013) doesn't use Ajax and requires opening a new page (slowly, as they don't use Java's built in thread-pools but spawn new threads, because the system has to run at a customer site that uses Enron's custom implementation of Java 1.3 on an AS/400) to make an changes.