#[1]Kostya's Boring Codec World » Feed [2]Kostya's Boring Codec World »
  Comments Feed [3]Kostya's Boring Codec World » Why I still like C and
  strongly dislike C++ Comments Feed [4]alternate [5]alternate
  [6]alternate

[7]Kostya's Boring Codec World

  Kostya's Rants around Multimedia
    __________________________________________________________________

  [8]« ZMBV support in NihAV and deflate format fun

Why I still like C and strongly dislike C++

  This comes up in my conversations surprisingly often so I thought it’s
  worth to write my thoughts down instead of repeating them again and
  again.

  As it is common with C programmers, C was not my first nor my last
  language, but I still like it and when I have to write programs I do it
  in C. Meanwhile I try to be aware of modern (and not so modern)
  programming languages and their trends and write my own
  multimedia-related hobby project in Rust. So why I have not moved to
  anything else yet and how C++ comes to all this?

Why C is not the best language

  First, the obvious statement that there is no such thing as “the best
  programming language”. Each language has its best use case scenarios so
  while you can write raytracing in Excel, it’s better be done in some
  other language. So it’s good to know programming language limits and do
  not complain that web servers are not written in Fortran and hardly any
  app uses Perl or C++ as internal scripting language. C may be
  considered not good for the following reasons (beside simply being too
  old and not fast-developing but that’s a matter of taste).

  C has syntax that is ambiguous at the times (e.g. * may be a binary
  multiplication operator, an unary dereference operator, or used to
  declare a pointer; the fun with typedef deserves a separate essay).

  It is not safe e.g. out of bounds array access is rather common and
  there’s no runtime check for that while e.g. Borland Pascal let alone
  something more modern had it (even if you could turn it off in
  compilation options for better performance). And the pointers make it
  even trickier to keep everything in order. Plus some other things like
  calling a function without a prototype declared so you can easily pass
  a wrong type of argument to it.

  Rather limited standard library. Some other languages may have even web
  server (or at least all building blocks for one) out of the box, C
  standard library lacks even on containers.

Why C despite all that

  The reason why I still like C is that it is a simple language. Simple
  in a sense that it is easy to express ideas and what to expect from it.

  For example, if you want to retrieve an array value with two offsets,
  one of which can be negative, in C you write arr[off1 + off2] while in
  Rust it would be arr[((off1 as isize) + off2) as usize]. And C-style
  loop is often shorter than Rust idiomatic way with iterators combined
  together (of course the former is also allowed in Rust but it’s frowned
  upon with linter always suggesting to replace it using iterators).
  Similarly memset() and memmove() are powerful tools.

  And in most cases you know what will compiler produce—what would be
  memory representation of the object and how you can reinterpret it
  differently (I blame C++ for making it harder in newer C standard
  editions but I’ll talk about it later), what happens on the function
  calls and such. C is called portable assembly language for a reason,
  and I like it because of that reason.

  So to use car analogy, it is like a sports car with manual transmission
  that gives maximum performance—but you can easily damage transmission
  or even engine if you mess with clutch and gearbox and of course you
  can drive off the road if you push gas pedal too hard. Yet more of the
  engine power goes to the wheels compared to the automatic transmission
  and you can predict its behaviour and do tricks not possible on other
  cars (because there you’d have to fight those automated controls).

So how C++ is involved here?

  And moving to C++, I don’t hate it. If you use it and like it, fine. I
  can’t deny that compared to C it offered two advantages: better program
  structuring (with namespaces and classes, Simula was good for something
  after all) and RAII concept (having constructors to initialise object
  on creation and destructors to clean it up on destruction, to put it
  oversimplified; if you develop this idea further you can come up with
  Rust lifetimes). But in the same time it also has two features that
  make me strongly dislike it.

  First of all, it’s the holistic nature of the language. If some other
  programming language has a popular feature, it will end in C++ too. In
  result you have you have C++ standard being reviewed every couple of
  years with more features added every time. In result you have a
  monstrous language that nobody can know in full, with many features
  being duplicate of the other features. And everybody essentially picks
  a subset of C++ and writes in it ignoring the existence of other
  features. Plus there’s no standard way to signal features from which
  C++ edition you’d want to use. In Rust they have crate-wide edition. In
  C++ IIRC they wanted to introduce epochs for the same purpose but it
  didn’t take off. And a fun thought—I encounter news time from time that
  somebody single-handedly wrote a functional C compiler (and in
  reasonable time too) but I don’t remember seeing the same news about
  C++ compiler even once.

  Another thing is that C++ is not just multiple languages in reality but
  also it’s a meta-language aka templates. I understand what it is for
  and agree it’s a better thing than C preprocessor for type-independent
  code. But in reality it seems to spawn hideous monstrous code including
  the shift from “header file for declarations, compiled code for the
  actual functionality” to “header file contains all the code that gets
  instantiated in the project including it”. I don’t like long
  compilation times and this approach encourages them.

  And finally, I could ignore C++ existence had it not been bolted to C
  and giving a bad influence on it. I’m not talking about C/C++ and “you
  say C that means you know C++”, I’m talking about the coupling having
  bad influence on both standards and compilers. On one hand, C++ got a
  huge boost from being based off C, on the other hand it would probably
  be better now without most of C legacy (of course it tries to get rid
  of it by making it obsolete bit by bit but the legacy support is still
  there). But would e.g. C++24 as a separate language based in C++21 with
  most of outdated stuff thrown out be as popular? I doubt it.

C++ compiler influence on C

  The related effect is that C gets treated as C++ without some features.
  The infamous case is Microsoft C-ish compiler that did not bother
  supporting C99 features until 2015 edition (and even then it still
  preferred bug-for-bug compatibility because the customers might be
  shocked to find out that variadic macros finally work there). But the
  same approach can be seen in both the standard and other compilers, and
  those are related issues.

  The principal problem is that both C and C++ standards are written
  based on the input from compiler developers, and those are mostly C++
  developers (and sometimes it feels they know nothing about the
  real-world programming and think it should just fit their views, but
  that’s a rant for another day). I do not follow the standard
  development but I’m pretty sure that the most annoying aspects in C99
  and later come from those compiler developers. And those made their
  considerations for C++ where it makes more sense but it was forced on C
  as well to make the compilers easier.

  I’m talking of course about “undefined behaviour” and how compilers
  treat it. This has become a popular scarecrow (your code relies on
  two’s complement arithmetic so it has undefined behaviour and the
  compiler can [DEL: throw :DEL] optimise out the whole block of code!).

  In my opinion there are four kinds of behaviour that are treated as a
  big no-no only while half of those deserve this:
    * Architecture-defined behaviour (i.e. what depends on CPU
      architecture). That includes mostly arithmetic. For instance, if I
      know that my target machines use two’s complement arithmetic (yup,
      no CDC 6600) why the compiler (that is supposed to know target
      architecture as well) would assume that it should behave otherwise.
      Because then it can perform some theoretical optimisations better?
      Hmm… The same applies to bit shifts as well. If I know that on x86
      it ignores high bits of shift amount and on ARM negative shift left
      means shift right why I can’t exploit that fact for my program just
      for that architecture? Integers having different sizes on different
      platforms are acceptable after all. Just issue a warning about
      non-portability and let me continue with it;
    * Pointer magic and type-punning. This feels forced exclusively for
      potential compiler optimisations. I agree that memcpy() for
      overlapping memory regions may not work correctly depending on its
      implementation (modern x86 implementations start copying from the
      end) and relative position of the addresses, but the other rules
      are less reasonable. That includes working with the same memory
      area using two pointers of different type simultaneously. I can’t
      imagine why it should not be allowed if not for hindering compiler
      optimisations (it can’t be an alignment issue). This culminates in
      impossibility of converting e.g. int to float using a union. Linus
      [9]ranted on it so I should not repeat the arguments. But to me
      this feels like something done either for better compiler
      optimisations or because C++ demands it—because of the type
      tracking (you don’t want to put one class instance into a union and
      retrieve it as completely different class difference; it may do
      something with optimisations as well);
    * Implementation defined behaviour (here it is not exactly what C
      standard means by it). My favourite example is function call:
      depending on calling convention and compiler implementation the
      function arguments might get evaluated in completely random order,
      so the result of foo(*ptr++, *ptr++, *ptr++) is undefined and
      should not be relied upon even if you know the target
      architecture—what if they’re passed in registers (like on AMD64),
      the compiler is free to calculate value for whatever register it
      sees fit.
    * Completely undefined behaviour. This is also the case where it’s
      hard to argue with the standard. The most prominent example is
      violating the rule about changing variable state just once in
      single statement, like the famous i++ + i++ or even worse *ptr++ =
      *ptr++ + *ptr++.

  Since C++ is higher-level language than C (while it has most of the
  features from C they are discouraged from using, you should use
  reinterpret_cast<> instead of direct type case and references instead
  of pointers, etc etc) you’d not expect C++ programmers to understand
  low-level code as good as C programmers (that’s just a statistical
  observation, of course it varies for individual people). And yet
  because of abundance of C++ programmers and C/C++ coupling you often
  have C compilers extended to support C++ and rewritten in C++ as well
  to accommodate for the complexity (this has happened to GCC and you
  have very WTFy GDB with C++ code in .c files). So you need C++ compiler
  to compile C compiler which is sad (but pure C compilers like LCC, PCC
  and TCC are still here luckily).

Conclusion

  To summarise it, I like C for its middle-level position where it’s
  still possible to do low-level things like manipulating memory contents
  with ease while enjoying the benefits of high-level language (that do
  not get in your way); and my strong dislike for C++ comes from its
  design choices (though some claim it was not designed but rather simply
  happened) and that those design choices affect C standard and compilers
  making it less the language I like.

  Well, at least it’s impossible to replace C90 with C90 Special Edition
  and pretend the original has never existed.

  This entry was posted on Wednesday, May 26th, 2021 at 11:40 am and is
  filed under [10]Useless Rants. You can follow any responses to this
  entry through the [11]RSS 2.0 feed. You can [12]leave a response, or
  [13]trackback from your own site.

10 Responses to “Why I still like C and strongly dislike C++”

   1. [14]mee says:
      [15]May 26, 2021 at 7:15 pm
      Ah, what about D?
   2. [16]Kostya says:
      [17]May 27, 2021 at 12:09 am
      That is an interesting language that (IIRC) lost its chance because
      of the compiler availability. I don’t have much to say about it
      except that now there are other languages trying to fit the same
      niche. As for me, they all have a right to exist.
   3. Peter says:
      [18]May 27, 2021 at 12:19 am
      Agree. Why no mention of Baidu’s new language?
   4. Matthew Fernandez says:
      [19]May 27, 2021 at 12:36 am
      FWIW some of the problems you refer to have been addressed by
      recent standards. C++20 mandates two’s complement integers. And
      type punning through a union is no longer UB as of C99.
   5. [20]Kostya says:
      [21]May 27, 2021 at 12:41 am
      @Peter
      It does not affect C even if it came from Plan9 version of C. And I
      don’t know what to say about it beside that defer is a nice
      concept.
   6. [22]Kostya says:
      [23]May 27, 2021 at 12:53 am
      @Matthew
      From what I can find, type punning is UB exactly in C99 (not before
      and not after). And in this post I wonder more about how they
      became problems in the first place.
   7. Joseph E Dante says:
      [24]May 27, 2021 at 12:56 am
      C was the slayer of many pop languages of the 80s like PL/1, Basic,
      Cobol, Pascal but eventually succumbed to the concepts of Objects
      in the form of C++.
      I think many of us by the 90s had our own libraries for data
      isolation, link list, and memory control and didn’t need fancy
      pants languages like Java or C++.
      I still use my old libraries to crank out very powerful programs in
      a few lines of code that compile and run extremely fast.
      Unfortunately, many programmers I worked with were Basic (pun
      intended) programmers who need to be somewhere and did have time to
      write very clean code, so Java was born. Java solved the memory
      leak problem, link lists, and data isolation so junky programmers
      were less junky.
      Unfortunately again, compiler writers needed to junk up another
      language and we have modern-day Java.
      I’m not a language guy like the author of this article, I just need
      to get stuff done easily and quickly and C is my best friend
      always. Thanks, Ritchie.
   8. [25]Kostya says:
      [26]May 27, 2021 at 1:21 am
      I disagree that most of the listed languages died because of C.
      PL/1 was C++ of its time with the C++ problems (too many languages
      to chose from, too hard to write a decent compiler, maybe it’s the
      hardware limitations that allow LLVM to prosper now prevented us
      from having too complex compilers back in the day). BASIC was
      popular in the 1980s and enjoyed its popularity in form of Visual
      Basic and then Visual Basic for Apps until it was replaced by VBA2
      aka Python. COBOL has never been popular with the major crowd and
      it’s still in use in its niche and it’s not going away from it.
      Pascal was intended to be an educational language (like BASIC) so
      while it enjoyed popularity as a systems language because of MacOS
      and Borland, it was still limited for larger tasks. Why Delphi
      didn’t keep its popularity is another question.
      As for more modern languages, Java was a product of the time—and
      the time demanded a safe language for less educated programmers
      because salaries are high and hardware became cheaper. And what do
      we have now for popular languages? Mostly something suitable for
      coders who can search what library to use in their product. As I
      briefly mentioned in the post, C++ seems to move in the same
      direction.
      Also I’m not a language guy myself, I just prefer to be aware of
      more than one language. Fun fact: back in university out data
      structures course was in C but one of the lectures was about Lisp
      and its “everything is a list” approach. You can program better if
      you know the different approaches to solving a problem.
   9. Zyx says:
      [27]May 27, 2021 at 9:22 am
      Nice sum-up, the C/C++ conflation has definitely harmed C. Any
      words on Clang compiler?
      COBOL has never disappeared indeed. Niche – and seemingly
      ill-designed – as it is, i wanna learn it. Too bad i don’t have a
      mainframe in the basement.
  10. [28]Kostya says:
      [29]May 27, 2021 at 9:38 am
      Clang seems to be a side project for LLVM which was written in C++
      right from the start. So the same problems with C++ mindset apply
      there as well.
      As for COBOL, I think you can find a compiler for something
      non-IBMy too. Or some zOS emulator hopefully. I understand why
      COBOL was designed as it is (and why it still makes sense to learn
      it for a retiring programmer).

Leave a Reply

  [30]Click here to cancel reply.

  ______________________ Name (required)

  ______________________ Mail (will not be published) (required)

  ______________________ Website


  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________
  __________________________________________________________

  Submit Comment

  Currently you have JavaScript disabled. In order to post comments,
  please make sure JavaScript and Cookies are enabled, and reload the
  page. [31]Click here for instructions on how to enable JavaScript in
  your browser.
    __________________________________________________________________

  Kostya's Boring Codec World is proudly powered by [32]WordPress
  [33]Entries (RSS) and [34]Comments (RSS).

References

  1. https://codecs.multimedia.cx/feed/
  2. https://codecs.multimedia.cx/comments/feed/
  3. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/feed/
  4. https://codecs.multimedia.cx/wp-json/wp/v2/posts/2177
  5. https://codecs.multimedia.cx/wp-json/oembed/1.0/embed?url=https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/
  6. https://codecs.multimedia.cx/wp-json/oembed/1.0/embed?url=https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/&format=xml
  7. https://codecs.multimedia.cx/
  8. https://codecs.multimedia.cx/2021/05/zmbv-support-in-nihav-and-deflate-format-fun/
  9. https://lkml.org/lkml/2018/6/5/769
 10. https://codecs.multimedia.cx/category/useless-rants/
 11. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/feed/
 12. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#respond
 13. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/trackback/
 14. http://no/
 15. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217293
 16. https://codecs.multimedia.cx/
 17. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217294
 18. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217295
 19. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217296
 20. https://codecs.multimedia.cx/
 21. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217297
 22. https://codecs.multimedia.cx/
 23. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217298
 24. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217299
 25. https://codecs.multimedia.cx/
 26. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217300
 27. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217301
 28. https://codecs.multimedia.cx/
 29. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#comment-217304
 30. https://codecs.multimedia.cx/2021/05/why-i-still-like-c-and-strongly-dislike-cpp/#respond
 31. http://enable-javascript.com/
 32. http://wordpress.org/
 33. https://codecs.multimedia.cx/feed/
 34. https://codecs.multimedia.cx/comments/feed/