How Relevant is C in 2014?
Nerval's Lobster writes: Many programming languages have come and gone since Dennis Ritchie devised C in 1972, and yet C has not only survived three major revisions, but continues to thrive. But aside from this incredible legacy, what keeps C atop the Tiobe Index? The number of jobs available for C programmers is not huge, and many of those also include C++ and Objective-C. On Reddit, the C community, while one of the ten most popular programming communities, is half the size of the C++ group. In a new column, David Bolton argues that C remains extremely relevant due to a number of factors including newer C compiler support, the Internet ("basically driven by C applications"), an immense amount of active software written in C that's still used, and its ease in learning. "Knowing C provides a handy insight into higher-level languages — C++, Objective-C, Perl, Python, Java, PHP, C#, D and Go all have block syntax that's derived from C." Do you agree?
Si.
Relevant C
2B || !2B
Either learn what you're doing
Or stick to the Wii
Burma Shave
Get thee glass eyes, and, like a scurvy politician, seem to see things thou dost not.--King Lear
Those widgets the clueless newspaper reporters and marketers call 'the internet of things', otherwise known as embedded systems, depends on Linux and C. So therefore C is 'the next big thing'.
Because it's extremely dangerous and a lot of people are still using it. The 'standard' standard library is so full of security holes it's not even funny, and attempts to 'improve' it over the years have mostly been unsuccessful because the bad coding patterns still exist.
C is a great language, it's just that most humans are incapable of using it safely and securely. It's like a .45 with a downward-pointing barrel. It's all too easy to shoot yourself in the foot.
For full disclosure, I used to be an avid C programmer, until I realized the harm I was causing myself and others. It's like when you drunk drive and think you're just fine. It takes an external perspective to realize how reckless your behaviors are.
A fool and his hard drive are soon parted.
C is the high-level language there. If you want actual control over your target, you'll need to use assembly.
Is there another OS/system programming language that is universally accepted as a reference, rather simple to learn, available on virtually any OS, real fast? I mean, go is nice and multi platform and powerful, but it is not even close to C popularity.
C++ should have been C successor, but it is too complex to be.
If you write a good useful library in C, it can be used from almost any other language, with little effort. If you write your library in any other language, you limit its use to a handful of related languages. Also, properly written C can be very portable to a wide variety of systems.
In Murphy We Turst
As to why there are more threads related to C++ on the Internet, easy, it's because C++ is a lot more complicated and complex to grok. I need as much help as I can with some of its tortured constructs and seldom used idioms. C is more straightforward (even if there are plenty of tricky things in it, which the seasoned programmers will either know how to use or steer well clear of).
Non-Linux Penguins ?
Lots of old traps in there, I stopped about 5 years ago with this book, needs a lot more work, but covers the basic "ooops" events. Thankfully at least with things like Valgrind / CLANG|gcc a lot of the older dramatic mistakes can be picked out quickly.
"C of Peril" - the book (pdf, free) at http://www.pldaniels.com/c-of-...
Then he must be in his mid-40s because I fully agree with him.
C is almost ML because almost all features of the langage can be directly translated into a few assembly instructions. This is also one of the last languages that still provides full control over memory and pointers.
C can be OO. It does not provide OO features such as inheritence or dynamic casts but they are easy to emulate with structs and macros. See forIf you want to create compiler for a new langage today, it is far easier to generate C instead of ASM. exemple the Gobject API. This is clearly not the most elegant way to do OO but it works and it can be as efficient a true OO langage.
I was and still am a pretty accomplished C prorammer, and can find my way in assembly. Then C++ came along and everybody seemed to jump on that bandwagon. I couldn't and many of my collegues either. When you have progressed to far along the procedural path, it seems to be impossible to wrap your head around the object oriented paradigma. That is why I also never got into Java.
Paai
You need to progress through modular programming and abstract data types. Then OO makes a lot of sense. Well written, highly modular C code with good abstractions tends to resemble well-written C++ without operator overloading in my experience.
Hell, well-written modular programming resembles well-written OO programming (since the later can be seen as a natural extension... or conclusion of the former.) Well-written procedural code must exhibit characteristics of modular programming.
What happens with C++ (specially at the beginning of its development) is that everybody tended to use every single goddamend feature, abusing operator overloading (and later templates). So C++ became "equivalent" to "overloading gotcha and magic-behind-the-curtains" soup smeared over a tangle of classes in an inheritance tree from hell (in many ways, not dissimilar from Java at the beginning with its own gotchas.).
One can program clean C++ with very simple semantics, using operators to the bare minimum, using templates judiciously, knowing when to use virtual and always implementing the big three (default constructor, copy constructor and = operator.)
If you can modularize your procedural code and how to layer your abstractions, then you know how to split your code into modules and classes. You know how to encapsulate and delegate responsibilities. That is key for developing cleanly in C++ (or Java or C#... or in any language for that matter.)
The C language has a stable ABI, and it is the only mainstream language that can make such a claim.
C is very much still relevant - most of the deeply embedded computer firmware is written in either assembler or C, where the bit twiddling capabilities, compactness of the language and efficient generated code are of high importance. All those ATMegas, PICs, 80x51, Z80, Renesas, small ARM Cortex cores - chips that are too small in terms of available memory to use higher level languages and OSes effectively. Essentially, if you are writing "to the metal", you are most likely going to use C, assembler and (rarely) C++. Those chips costs peanuts and are pretty much everywhere, controlling everything from your toaster to brakes in your car ...
Programming is not only about the desktop and web, you know.
Even on more "grown up" platforms you will find C in the network code, most of system programming is done in C, C with its standardized ABI is an interface language (e.g. you can load a C-interfaced DLL into Python or Java, for example) and many many other applications. I would say that knowing at least the basics of C is as much a must for any programmer as knowing basics of English - unless all that you do are web apps in Javascript.
C++ is C
I used to believe in this until I had to work on both. Although one can compile best-practice C with a C++ compiler (sans the gotchas), that glosses over the idiosyncrasies of each language. C does not have initializers as in C++.
More importantly, it does not have references, type-safe casting operators and its template language is not turing complete as in C++. These differences will never go away, and these differences alter completely the type of design and implementation of your code and your abstractions.
Not to mention the C++ rules of PODs versus everything else which affect how we link C code with C++ code (and viceversa.) And modern C++ heavily uses templates in manner that makes the language resemble something else entirely. Whether that is a good thing is highly subjective, but whatever.
So from a practical point of view, it is sane to treat both languages as fundamentally different.
When we program in a language (be it Ruby, Java, C or C++ or whatever), we ought to do so in the idiomatic way that naturally exploits the best capabilities of the language. So with that in mind, we cannot treat C and C++ as the same language (and it is not quite accurate to compare modern C++ as a superset of the former, regardless of historical evolution.)
I do believe, however, that is very important, if not fundamental, to understand C semantics to use C++ effectively. The fundamental semantics behind the primitive types and control structures remain more or less the same. And I've always found that C++ programmers without a good background in C tend to make certain mistakes when they need to operate with pointers (since they are so used to work with references.)
Furthermore, integration of C with C++ is not an uncommon task, and development of C++ code with that in mind is paramount. It is very hard to do that without a good understanding of C.
To clarify: "Small target" means memory (RAM/Flash) is measured in kB, sometimes even in bytes.
You still have Python-capable processors for embedded systems if you can't afford to learn C.
As far as target size goes, that thing does not qualify as "small target".
FWIW, I've been struggling with LPC4300 series processors.
Those chips look like they're on the large end of "small target". Cortex-M4s are already pretty beefy CPUs.
The open source toolchain is just so bad that your CPU hard faults on first attempted function call (most likely due to incorrect memory maps).
You can usually get pretty detailed reasons for a hard fault if you dig into the appropriate CPU registers (HFSR, etc).
I'd check the linker command file. Setting up a basic memory map isn't that hard - it's the not-so-basic stuff where things get interesting (copying functions to RAM for execution, etc).
It's as if engineers could skip calculus because there are automated systems that will do it for them. Even if they never work directly with calculus, the experience is critical to being a competent engineer.
Yes, C has features/bugs that can be really ugly. But as a professional you can make a system like C and it's runtime libraries work then you are much better equipped to do other complex tasks. The experience can result in careful habits that will help your entire career.
Why is Snark Required?
C started out with high level "constructs" that were basically the operators of the PDP-11 and VAX processors from DEC. While those constructs have mapped well to other processors, virtually every statement in C originally compiled to one instruction on those processors.
To this day, C still gives you the power and flexibility of any low-level language worth it's salt, and ample opportunity to hang yourself and your code. Don't forget -- C++ originally targetted C as it's output, not machine code. C has similarly provided the "back end" for no small number of special-purpose compilers.
Then there are the operating systems and device drivers that have been written with it, and all the embedded systems logic for devices all and sundry.
C will never die any more than assembly or COBOL and FORTRAN will. There will always be those special-purpose high-performance tasks where it is worthwhile to use C instead of a higher level language. Just as there are times where it still makes sense to drop even lower and into assembly.
You go ahead and try to bootstrap an entire C++ implementation so you can write a kernel in it. Good luck with that. Getting a C library framework running on a bootstrapped kernel is hard enough. C++ would be orders of magnitude harder.
I do not fail; I succeed at finding out what does not work.
We're talking about C. You want the zeroeth post.
And every good butcher should be a great farmer, every good soldier an expert weapon maker, every good driver a world class mechanic ;)...
Strawman argument.
The OP doesn't argue that people whose profession is different from programming should be able to program. He argues that a good butcher should be able to kill with a mechanical tool, not just the fancy bolt gun the slaughterhouses have now. That a good driver should be able to drive stick-shift even if his car has automatic.
And I agree. When I was in university, I tortured students with proper input handling in C until they got it, until they understood that unless they check their input conforms to whatever specification they make for it, instead of just checking the exceptions they can think of, I will always find a way to break their program by, say, keeping my finger on the "a" key for 3 seconds and overflowing their buffer. I'm pretty sure they're not the ones making web applications less secure today because lazy programmer doesn't do form validation.
Learning the basics of programming on a not-holding-your-hands platform makes you understand what's going on and what can go wrong. If you learn programming on a training wheels framework, your programs will almost certainly be subject to all kinds of injections, overflows and other attacks whenever the framework doesn't protect you 100%, or requires you to make an explicit call to get those benefits.
C is a great language to learn programming. Yes, you'll swear a lot and you'll hate the computer, your teacher and the world in general, but when you come out of that bootcamp, you're a marine and not some third-grade wannabe trooper with a 10 minute life expectancy once the shit hits the fan.
Assorted stuff I do sometimes: Lemuria.org
I'm not sure I agree. I learned C++ first and then C a year or two later, and I can manage raw pointers just fine, thank you. I just think you're crazy if you do it willingly when there are much better alternatives available.
I've seen plenty of C turned C++ programmers who essentially treat classes like a giant package for wrapping up loosely related functions into horrifying kitchen-sink classes. They don't know how to create proper interfaces, and pass all sorts of raw pointers around, managing memory manually, even though there's often no reason for doing so. In short, they've never dropped the habits they acquired from C. And frankly, bad C++ is arguably worse than bad C.
One could argue that this is a result of learning C before C++, but honestly, it's really just a matter of programmer skill and/or competence. A C programmer should be able to learn the ins and outs of OOP and generics / templates, and a C++ programmer should be able to drop down to low-level pointer-intensive code if they need to. If not, it just means that they stopped trying to learn new things - nothing more than that. Or, maybe no one ever took the time to point out better methods of writing code.
Anyhow, C is a dangerous, crusty language, but it's not going away anytime soon due to it's sheer pervasiveness, utility, and efficiency. It's essentially the common denominator of languages, which is why so many libraries are written in C. Just about any language can interop with C (or it generally doesn't get off the ground). Moreover, entire operating systems are written in C, meaning it's going to stay relevant as long as those OSes are around, and I don't see them fading away in the near future.
Irony: Agile development has too much intertia to be abandoned now.
I have written embedded Pascal. Never ask me to do it again.
Once. Gave me a real appreciation for high level languages like C.
And, yes, it was an embedded application. No user interface, the controller talked to the device, the device ran some very precise valves. It was actually a fun month getting all that working.
Best Slashdot Co
C++ is not the only way to do object programming. If fact this is probably the most complex and crappy way to do it. A lot of others language have proven that object programming can be more simple. C is late in the object programming game and can take this as an opportunity to do it the right way.
" don't really seem to understand the difference between pointers and C arrays"
Well, because there isn't one at the language level. The array syntax using square brackets is only a syntactic sugar for pointer arithmetic, nothing more.
There is a difference between an array and a pointer.
char a[100];
char* b;
b = a; // Fine // Not fine.
a = b;
If you read the standard, the language used is that, in an expression, an array "decays" to a pointer with the rule being that you get a pointer to the array's first element. The "array is not a pointer" rule is further demonstrated by passing an array to sizeof (as viol8 points out).
All I want is a secure system where it's easy to do anything I want. Is that too much to ask ~~ Randall Munroe
Yep, this is true. There is still work for the odd embedded or Linux kernel hacker guy, but from a sole business perspective, mastering C is not terribly useful.
Ok I will bite. Now I don't claim that C is on the same level than ASM, but you need to compare it to current languages. Languages like Python or JavaScript, they abstract out almost everything about the machine you are running them on. With C you program against a reasonably close abstraction of the real machine. In many cases you can hand compile the C code to ASM.
Take for example the JS expression $("a").addClass("blue"). This expression written in C would take up something around 100 lines of code, simply because the machine you program against does not understand high level concepts. Even simple concepts like a string are not understood by C.
I love programming in C, but in whole ecosystem of languages it is on the low end.
I have issues with that notion, though. There's this popular perception among hardcore C programmers that C++ is "C with objects", and since they don't like or don't feel the need to do object-oriented programming, it's pointless for them. But C++ is a thousand times more than "C with objects". And even when it comes to objects, the most important ones aren't the ones you make yourself, but STL. Especially with the latest versions of C++. I just recently had to downgrade a simple app from C++11 to C++03 to support old compilers, and my god, I had forgotten what a royal pain pthreads are versus std::thread with a lambda argument. And if I had been forced to go all the way down to C, and thus would lose the std::list that simplified holding the threads' arguments. It would have been a page or two of code for what's a single line in C++11. And with far greater proclivity for bugs.
I once was one of those "hardcore C programmers" who just saw C++ as "C with objects", and deliberately avoided using it and learning any more than I had to. But the more I learned, the more I came to appreciate it. I do of course make and use my own objects... but that's not really the most important aspect of the language. It's all of the countless features to automatically manage memory, data structures, ensure program correctness, and vastly reduce pointless verbosity that make C++ so important.
"We consider that six courts and an asylum claim are a rather odd way of returning to Sweden within a month."
Android apps can use C for native code, and many do for performance reasons (e.g. games) or to access lower level OS functions (e.g. interfacing with USB devices).
const int one = 65536; (Silvermoon, Texture.cs)
SJW, n: "Someone I don't like, and by the way I'm a fuckwit" - AC
C is not intended to be a beautiful language. C is intended to give you as much control over the raw machine as possible, without going to assembler level and with (these days) reasonable portability. If you compare C and Pascal, then you have failed to understand the purpose of C.
Most ACs are not even worth the keystrokes to insult them. Be generically insulted by this and ignored otherwise.
OOP is a style, not a language feature. Sure many languages make this easier to do, but writing OOP in C is certainly possible, as many of us can attest.
William of Ockham had no beard. The most likely explanation is that it was chewed off by squirrels every morning.
We're talking about C. You want the zeroeth post.
You have to remember, there are two kinds of people in the world:
1) Those who begin their indexes at 1.
-and-
1) Those who begin their indexes at 0.
But C++ is a thousand times more than "C with objects".
I believe the above quote speaks for itself...
"C++, Objective-C, Perl, Python, Java, PHP, C#, D and Go all have block syntax that's derived from C"
And C got the block syntax from B which got it from BCPL which was a simplified version of CPL which was influnced by the first block structured language, ALGOL.
I was taugh ALGOL at University, though I had already been "mentally mutilated beyond hope of regeneration" by BASIC before that...
That's not even Javascript.
How many times more this year (only 22 days left!) are we going to see these types of "articles"? Give it a rest. C, COBOL and Fortran will be around long after all of you are dead.
This may be true for new code, but when maintaining C++ code written by others, not so much. Everyone has a different set of "features they like".
There's also OpenCL which is far closer to C than the rest of them, and that is a language that is still up and coming.
First off I'd consider C++ and Objective-C to both be variants of C. And you can make a fairly good case that Java is also a variant of C.
That being said there is a good use case for C by itself. Lots of algorithms execution times are of forms like R*n^2 + S*n + T. For N large, A is all that matters. For N small T can often be the dominant factor. The C language, like assembly excels at getting the execution times for T down. However for most business processing execution time isn't really all that important since n isn't large nor is T particularly big. In which case programmer efficiency matters a great deal.
Safe and secure are two factors that are important. Here are some others:
a) Code can be written quickly
b) Code is portable
c) Debugging times are low
d) Code is reliable, i.e. factors of the execution environment don't effect computed results
e) Problem domain is large
f) Has a huge range of specialized libraries
g) Has a following so that it is easy to hire in the problem domain
h) Can be learned quickly
i) Has a set of primitives that pair well with the problem domain
j) Code executes quickly
k) Code makes efficient use of system resources
etc...
Any decent language is going to excel at some aspects in exchange for being dreadful at others. Popular languages are popular because they excel at particular problem domains. C excels in 2014 where safety isn't a major concern because most C programs don't have a complex API, or where execution speed is paramount.
But C++ is a thousand times more than "C with objects". And even when it comes to objects, the most important ones aren't the ones you make yourself, but STL.
The STL.... the thing that drove me from C++ in the first place with its horrible non-portable implementations due to non-standardized name-munging amongst different compilers. (Note: I'm sure this situation improved from the date(s) I'm referencing, but even the thought of the STL brings back old nightmares)
And my most recent forays with C/C++ were thankfully STL free, as it was mostly straight C code, or merely linking into C code.
The cesspool just got a check and balance.
The downside of C++, is you can't look at the code and know what happens at the machine level. Joel Spolsky describes it below: (in an article on variable naming)
"In general, I have to admit that I’m a little bit scared of language features that hide things. When you see the code
i = j * 5;
in C you know, at least, that j is being multiplied by five and the results stored in i.
But if you see that same snippet of code in C++, you don’t know anything. Nothing. The only way to know what’s really happening in C++ is to find out what types i and j are, something which might be declared somewhere altogether else. That’s because j might be of a type that has operator* overloaded and it does something terribly witty when you try to multiply it. And i might be of a type that has operator= overloaded, and the types might not be compatible so an automatic type coercion function might end up being called. And the only way to find out is not only to check the type of the variables, but to find the code that implements that type, and God help you if there’s inheritance somewhere, because now you have to traipse all the way up the class hierarchy all by yourself trying to find where that code really is, and if there’s polymorphism somewhere, you’re really in trouble because it’s not enough to know what type i and j are declared, you have to know what type they are right now, which might involve inspecting an arbitrary amount of code and you can never really be sure if you’ve looked everywhere thanks to the halting problem (phew!).
When you see i=j*5 in C++ you are really on your own, bubby, and that, in my mind, reduces the ability to detect possible problems just by looking at code."
My opinion is, for code that lives closer to the OS (or the OS itself), where there are fewer lines of code but which run more frequently, C is king. For code that needs to multiply/grow/combine/evolve faster and still run fast, C++ is often a better choice.
And the solution to that isn't to ditch the language - you just reject code that does obtuse and sneaky things in your project. If multiplication of your objects doesn't make sense, then why on earth would you overload the * operator?
Even though a[i] and i[a] are the same thing in C (well, except for making the compiler's job harder), you shouldn't use them interchangeably in your code.
You shouldn't judge a language simply because it allows obfuscation. You should judge your coworkers for writing obtuse code.
No one says it was you who overloaded the operator. You may be looking at code someone else in your team wrote, or an ex co-worker, or an open source contributor -- and it could be even you and don't remember it. The point is, the reality is if you are given code to work with and you see i = j * 5, if it's C you know what it does; if it's C++, you don't, regardless of who wrote it.
I think the danger of that happening for low level, frequent-running, system code outweighs the flexibility that C++ gives you, and vice versa for app code.
If multiplication of your objects doesn't make sense, then why on earth would you overload the * operator?
If bit shifting your object doesn't make sense then why on earth would you overload the << operator
I can't really make up my mind on operator overloading. On the one hand it can make custom types far more pleasant to use. On the other hand because operators are more concise than function calls and you can't add new ones it's very tempting to abuse operators to mean something other than their original meaning. Heck it's so tempting that even the authors of the standard library did it.
note: i'm known as plugwash most places but i screwd up registering that here somehow in the past and now can't register
Here's the thing about c. If you're good enough to use it well (rare, I admit), the results can be made to be faster, more efficient, and more *clear*, meaning, you can actually see what's happening, while still remaining reasonably portable, than any other language. Even in the largest applications. Perhaps especially in the largest applications.
Until someone comes with something faster, c is *the* goto language for high performance coding.
As soon as you start sticking generalized objects in generalized boxes, as soon as you decide you can't manage your own memory, as soon as you decide you must have generalized abstraction (as opposed to specific, high-efficiency custom abstraction, boxes and objects), you're sacrificing performance, and you're probably sacrificing size and efficiency at the same time.
If what you're writing is a word processor, well, so what. But if you're writing real time goodness, or something truly CPU bound (like almost any AI undertaking, or SDR, or speech recognition, or object recognition, etc.), not using c is a mistake. Not to mention a waste of the eventual end user's resources. Just because there are CPU cycles available doesn't mean that it's OK to chew them all up, likewise available RAM. Operating systems can do more than one thing -- if they're not choked to death by some lumbering, clumsily implemented hunk of crap.
c is awesome. c is simple. But c is difficult, because you really have to know what you are doing. All that power at your fingertips means its 1000x easier to drive straight into a tree. You have to truly understand, on an intuitive level: stacks, memory management, objects, abstraction, how c statements likely map to CPU activity and instructions, and how to write clear code and documentation and a bunch of other stuff -- because it's up to you to manage all that stuff, and a failure in any of those areas is very likely to negate all the other advantages, or worse.
The only thing better is assembler, where you can *really* be efficient and produce ultra-fast code. But assembler isn't portable, and that, sadly, is usually the end of that.
I've fallen off your lawn, and I can't get up.