96

I code a lot in both C and C++, but did not expect C to be the second most popular language, slightly behind Java.

TIOBE Programming Community Index

I'm curious as to why, in this age of OOP, C is still so popular? Note that 4 out of the top 5 popular programming languages are "modern", object-oriented capable languages.

Now, I agree that you can use OOP in C to some extent, but it's sort of painful and inelegant (well at least compared to C++ I guess). So, what makes C so popular? Is it efficiency; being low-level; the vast majority of libraries that already exist or something else?

Craige
  • 3,781
mmirzadeh
  • 599

15 Answers15

145

A few factors that contribute:

  • C is ubiquitous. Whatever the platform, C is probably available.
  • C is portable. Write a piece of clean C, and it compiles with minimal modifications on other platforms - sometimes it even works out-of-the-box.
  • C has been around for a while. Back in the days when UNIX conquered the world, C (the UNIX programming language of choice) shared in its world domination, and became the lingua franca of the programming world. Any serious programmer can be expected to at least make some sense of a chunk of C; the same can't be said about most other languages.
  • C is still the default language for UNIX and UNIX-flavored systems. If you want a library to succeed in open-source land, you need fairly good reasons not to use C. This is partially due to tradition, but more because C is the only language you can safely assume to be supported on any UNIX-like system. Writing your library in C means you can minimize dependencies.
  • C is simple. It lacks the expressivity of sophisticated OOP or functional languages, but its simplicity means it can be picked up quickly.
  • C is versatile. It is suitable for embedded systems, device drivers, OS kernels, small command-line utilities, large desktop applications, DBMS's, implementing other programming languages, and pretty much anything else you can think of.
  • C is fast. Most C implementations compile directly to machine code, and the programmer has full power over what happens at the machine level. There is no interpreter, no JIT compiler, no VM or runtime - just the code, a compiler, a linker, and the bare metal.
  • C is 'free' (in both the beer and the speech sense). There is no single company that owns and controls the standard, there are several implementations to choose from, there are no copyright, patenting or trademark issues for using C, and some of the best implementations are open-source.
  • C has a lot of momentum going. The language has been popular for decades, so there is an enormous amount of applications, libraries, tools, and most of all, communities, to support the language.
  • C is mature. The last standard that introduced big changes is C99, and it is mostly backwards-compatible with previous standards. Unlike newer languages (say, Python), you don't have to worry about breaking changes anytime soon.
  • C is compatible. Most languages have bindings to talk to C. This means one can develop a library in C using standard calling conventions, and feel confident that almost any other language can link against that library. To name a few popular languages in widespread use: C#, Java, Perl, Python, PHP can all link against C libraries without much trouble.
  • C is powerful: if the language cannot do something, all popular compilers allow embedding assembler code which can do anything the hardware can do. Transitively combined with the above point about compatibility, this means C can act as a liaison between higher level languages and the "bare metal" of assembly.
tdammers
  • 52,936
92

I've always tended to blame the popularity of C on the need for a universal assembly language. It's combination of specificity at the machine level, standardization, and extreme portability allow C to function as that de facto universal assembly language, and for that reason I suspect its role there will continue indefinitely.

I should mention that I'm always a bit surprised when OOP is presented in programming courses as a sort of "final model" that is the only possible endpoint for good programming. Like many other aspects of programming, the value of OOP is a compromise between many competing factors, including how human brains organized information, how societal groups support software over the long term, and in the case of object-oriented programming, some pretty deep aspects of how the universe itself works.

And that last point is worth hammering a bit. Read further if you are interested in a physics-level exploration of why certain programming styles exist, how they work together, and where the world may be heading in the future as we expand further on such concepts...

An object in physics is anything that maintains recognizable coherence over time. That in turn allows simple creatures like ourselves to get away with representing the object using only a small number of bits, without endangering our survival too badly. But in terms of physics in the large, the number of things you have to get exactly right to make that kind of simplification easy and common is remarkably large. As humans we don't think about all of that much because quite frankly, we wouldn't be here if it were not true.

Sound too abstract? It really isn't. Imagine for example trying to navigate the road to your friend's house if instead of cars you encountered rapidly oscillating plasma fields and momentary condensations of matter moving with an enormous range of velocities. Such a scenario might cut rather deeply into socialization opportunities, yes? We need objects, we are objects, and the existence of objects provides us with an enormous and critically important level of simplification of the environment around us.

So let's pull all of that back around to software. What do objects in the real world have to say about objects in terms of programming?

Well, for one thing it means that what defines a "good" object in software should really be whether or not the type of data you are handling readily supports the idea of recognizable persistence over time.

With the definition, the easiest forms of OOP are easy to recognized. They are the ones that cop out a bit by using only data that is already "attached" or defined by some real-world, truly physical object like a person, house, or car. Even today, this is still too often the only definition of objects that people get in software courses. That's too bad, because even trivial object-oriented programs need a broader definition than that.

The second and far more interesting category of objects consists of what I'll call immortalized real-world events. By "immortalized" I mean things that at least briefly exist as a well-defined entity or collections out in the real world, but which then disperse and ceases to exist as physically meaningful collections. A symposium is a great example: The symposium exists for a short while as a decently well-defined collection of places and people. But alas, even the best conferences must end, and the individual parts that made them up move on to other activities.

But by using computers and networks, we can make such a transient symposium seem like a long-term object by capturing and maintaining a memory of it as a software object. A great many of the things we do with computers and databases amount to this kind of immortalization of transient events, in which we in effect try to make our real universe richer by capturing and extending it in ways that cannot possibly exist physically. E.g., have you seen a real Pandora lately? Such captures and extensions of real-world pieces help enrich and extend our own lives, economies, and choices in remarkable ways. This to me is the heartland of object oriented programming, the place where it has had, and continues to have, the most remarkable impacts.

A final category of OOP consists of objects that have no close connection to external events, but are instead the infrastructure needed to support our continuing extension of reality using immortalized objects from the real world. This is where you can descend all the way down to the (semi)metal of the computer, creating pieces of persistent reality that like the chemical elements of the real world can be combined quickly and in interesting ways to build new internal worlds. Mobile computing has helped promote the growth of this kind of highly recombinatorial approach, one that again in many ways mimics the recombinatorial features of the physical world. It is also hard: What may seem like a good choice may prove over time to have been an unexpectedly bad one, usually because it ends up blocking diversity and expansion instead of supporting it.

This last category also points the risks of using just one model for programming, since just like the real world, programmed worlds also need processes that don't correspond well to relatively unchanging objects. Earth is full of objects, but the sun is full of highly dynamic energy flows that ultimately are needed to "drive" the objects and activities on lower-energy earth. Similarly, in creating computing worlds there are cases where you must deal with flows and transformations and rapidly changing contexts that, while not very object-like in themselves, are nonetheless absolutely critical to enabling the simpler, more human-friendly objects used at higher levels. It is no coincidence that much of the programming done at the kernel level is not conspicuously object-like, or that it tends to rely heavily on languages like C that are more processing oriented. These are the deeper domains that complement the fascinating diversity we see higher up in computer generated worlds. Trying to force them into pure object models can be a bit like telling the sun it needs to be re-organized as a few billion tidy fireplace objects so that we can understand and navigate more easily from our humans-first perspective.

The other area where OOP can go awry is focusing too much on old object concepts.

Objects in the real world, and especially living objects, have an absolutely astonishing level of ability to interact with their environments in complex and subtle ways. Composable widgets that look each other over, do some compatibility and sanity checks, and maybe even figure out some new ways to interact come a lot close to the real-world biological concept of objects than do the simple frameworks and simple inheritance schemes that we tend to focus on (usually by necessity!) at the code level. This is one of the growth areas for objects in the cyber world, the more "agent like" approaches where reactivity to environment is the norm even within programming itself.

And so much for my "critique" of OOP! Still, though, I hope I've pointed out why creating a richer cyberworld means encompassing diversity of programming styles, rather than assuming that "just one" is all that is needed. My feeling is that the really interesting stuff is yet to come, no matter how mundane much of what we do now is!

Robert Harvey
  • 200,592
24

Firstly, you don't need OOP for everything, despite whatever dogmas regarding this have been popularized. Unlike Java, C allows function pointers and even closures which opens the door to functional programming and solves quite piece of the problem space OOP handles, because it provides the means of dependency injection. Also cautious use of macros can actually create some very nice things, as sglib proves.

In a weird way, one could see C as a good compromise between Java and C++. Please note I am not saying that C is in any way a mix of both. But in contrast to Java, it is rather powerful language while in contrast to C++ it has manageable complexity.

It is an old language, that has grown reliable and consistent, while not really growing more complicated. And all that aside, it has a giant eco-system and it simply runs everywhere.

back2dos
  • 30,140
21

C has an ABI(Application Binary Interface) C++ doesn't. This makes C more useful than C++ in certain instances. If I am going to write a library and be able to ship binaries for other people's use C++ is the wrong tool for the job. If I am going to write libraries that are going to be used by some other language again C is the right tool for the job. I have never heard of a language that didn't support FFI(Foreign Function interface) to C, on the other hand C++ won't work with libraries written in C++ if different compilers are used.

Basically it boils down to C filling a role that C++ is unsuitable for.

stonemetal
  • 3,381
12

Embedded systems and drivers are usually programmed in C. Aside from that there are tons of legacy C systems out there that are still maintained and extended.

EricSchaefer
  • 2,111
12

One advantage of using C over languages like C++ or Java is that there isn't a whole lot of magic happening under the hood. No constructors are run when items are allocated, and no destructors are run when objects go out of scope. There's no name mangling and no vtables. Performance is easier to predict; you don't have to worry about a garbage collector interrupting a routine and throwing off its timing.

Constructors, destructors, name mangling, vtables, garbage collectors, etc., can ease some of the complexity in the code you author, but then that complexity becomes part of the language itself, where you have little to no control over it. You may wind up with longer build times (annoying, but tolerable), larger runtime memory footprint (may or may not be tolerable) or slower performance. With C you can pare away some of that complexity until you're left with the functionality you need.

For example, the C++ string data type is light-years easier to work with than C-style strings, but it's a fairly heavyweight piece of code, and adds some heft to your image size. I've rarely seen anyone make full use of string's capabilities in any one program. C-style strings, while harder to work with, impose less of a penalty in terms of run time and image size, and for a particular problem may be more attractive for that reason.

John Bode
  • 11,004
  • 1
  • 33
  • 44
11

The same thing that makes a manual hammer popular in an age of pneumatic hammers (air hammers): C is still the right tool for certain jobs.

anon
  • 1,494
8

Simplicity, consistency and precision.

It is simple - you don't need a complex development environment, extensive libraries, or a virtual machine.

It is consistent - most C written 10 years ago could compile today.

Precision - it let's you get down to the level of the machine, knowing the memory locations as needed. This is great for performance and embedded hardware.

It's not for everything, bit it's still a useful tool.

MathAttack
  • 2,786
6

I cite two points from another answer, because they capture exactly the reasons why I still use C from time to time (it is not my main language of choice, though):

  • C is simple. It lacks the expressivity of sophisticated OOP or functional languages, but its simplicity means it can be picked up quickly.
  • C is mature. The last standard that introduced big changes is C99, and it is mostly backwards-compatible with previous standards. Unlike newer languages (say, Python), you don't have to worry about breaking changes any time soon.

I think this is very true. I learnt C during the early nighties: it was simple, few keywords and constructs, most of the job done by libraries. Then I did not use C for a few years. Around 2002 I needed a fast implementation of an algorithm, I installed a C compiler and implemented it. I know the language, I know what it is good for, what it is not good for (I would never implement a web application in C!), and it is just there when I need it. No surprises.

With C++ I had a different experience. I learnt it around 1995 and it meant a big paradigm switch from imperative to OOP. Great! I used it for several projects until 1999. For a few years I did not use C++ and when I picked it up again (2008) I found lots of new features already in the language, and even more planned (meanwhile introduced in C++11). I got the feeling I have to learn the language again.

As a developer, I prefer mature, stable languages. I like to learn a language once, to understand its design principles, what it is good for, and to use it when I think it is the right tool for the job. I also like to learn different languages and to pick the language that suites my need (C, C++, Java, Scala, Haskell, and so on). What I do not like is to have to learn the same language again and again because it gets developed further and further, and never reaches maturity.

IMHO, a programming language should have a clear, coherent, and stable design. I like the approach of designers like Niklaus Wirth: every time he felt the need for a different language, he designed a new one (Pascal, Modula-2, Modula-3, Oberon). I do not like languages that undergo important changes every 5-10 years: they are like moving targets and I never feel it is worthwhile investing my time to learn them in depth, because the version I am learning now will probably be obsolete in a few years anyway.

In this sense C is IMO a winner: it is good for certain applications and less appropriate for others, but it has the advantage that it is simple and relatively stable.

Giorgio
  • 19,764
4

I'm surprised that no one has mentioned Worse Is Better yet. It's over 20 years old at this point, but still eminently worth reading. While at times slightly tongue-in-cheek, it does a very good job of outlining how and why the expedient often wins over the ideal, using C (pitted against LISP) as one of its central examples.

2

You probably wanted to ask why people use C instead of C++ despite the fact that when you have a C compiler, you also usually have C++ compiler.

  • C language is much simpler than C++. I don't know any company that uses the complete C++ standard in their coding convention. Take a look at Google's C++ code style as an example: http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml
  • C is much faster to compile. Thanks to the lack of hard to compile constructs.
1

Because C has a huge user base. Yes it is a bit of a catch-22, but when I ask a question about C over on StackOverflow, I get the answer almost instantly. The same question about Python could take hours to get answered.

With respect to C++, it's IMO more complicated to learn. Furthermore, after having tried OOP for 10 years, I find it's not always useful, and often times it's easier to use procedural programming instead.

puk
  • 151
0

Nothing. TIOBE is a worthless index. If you actually look at their measurement, it's an absolute guess- at best.

DeadMG
  • 36,914
0

Lots of Legacy Software

Many companies cannot change, instantly all their code to C++ or similar.

Many companies cannot afford to change their code.

Many companies can afford to change their code, but don't care, or are "cheap".

Many companies are in the process of migrating, but, not yet finished.

Hidden Object Orientation

(Non Object Oriented) C source code designed as Object Oriented C source code, applications that are modeled with Object Orientation, and coded with "pure C", or tools that translate from "C++" or other O.O. progr. lang into C.

I heard that some video games are done that way. Some cross platforms tools also, and the GTK (GObject, GLibrary) visual interface library for the GNome Linux O.S. distributions.

umlcat
  • 2,206
0

I see some of the answerers give as to why C is the most popular, it's been around for a long time, it available in most platforms, free, etc.

But the same can be said about other languages, free Pascal for example - it's free, and supported for just about all platforms.

Pascal was invented around 1970, C was invented around 1972, so I think Pascal has been around just as long as C.

Personally I think C is the most popular language because there is just more open source code available out there to be reused by anyone. And yes it lower level than Pascal, so it's getting close to assembly but its a lot more readable than assembly.

I think there are just way too many programming languages out there. As programmers we have to know most of the important ones, but at the end there should be no need for that. One programming language can be implemented to do it all from building websites to iOS computer games.

C seem to be that global language, but I wish it would be something like Object Pascal. Why Object Pascal, it's a more readable programing language, OOP code does tend to be more reusable and less bug prone (in my opinion) than C.

Very large applications are easier to manage with Object Pascal than C/C++.

As to having a programming language that has been the some since the '70, and not liking languages that change every 5 or 10 years. As time goes technology advances and programming methods are improved. If a languages changes drastically every few years then it was probably not well thought out by its designer. But 1970 to 2012 is almost half a century, it's ok to make changes to a language in that time to incorporate advances used in Software development.

C itself has been revised several times. So, it's not better than other languages form that point of view.

gnat
  • 20,543
  • 29
  • 115
  • 306