C++20 Ranges Algorithms – Non-Modifying Operations(cppstories.com)
cppstories.com
C++20 Ranges Algorithms – Non-Modifying Operations
https://www.cppstories.com/2022/ranges-alg-part-one/
62 コメント
I'd be curiously to see how many people actually use modern C++ professionally. I've always been under the impression that adoption of the standard lags behind by like 7 years or so.
I work for an HFT firm. We have been using C++20 as well. Mostly C++20 concepts.
I work with a C++20 code base. By which mean... there is at least one C++20 feature in use, which means it won't compile with anything earlier than GCC 11. This reality is probably the norm anywhere you see C++20 job description.
We've been on c++14 for quite a while, and moved everything to c++17 a few months ago.
My company does a decent job at keeping up with the standard. Getting from C++11 to C++14 was challenging, and C++14 to C++17 took quite a bit of time, but we're on track to be on C++20 later this year.
Do you have a strategy for doing this? Since C++ stays relatively backwards compatible I would imagine there is lots of legacy code that gets untouched but newer features would go into the new stuff - with legacy code getting replaced only for big refactorings?
Our code tends to be shipped running on top of a relatively up-to-date version of linux. So we tend to go through the pain of testing/refactoring needed to get to the next version of C++ when we upgrade to the next stable version of linux that we're going to support.
that sounds about right, 5 years ago I was pleasantly surprised when large existing C++ code bases were C++11, now it's very common.
The last time I used C++20 features (modules) I caused a segfault in GCC. This was in December, iirc it was GCC 11.
Right now VC++ is the only viable option for C++20 modules, and even it isn't without warts.
It is kind of crazy that JTC1 is OK with producing entirely imaginary documents. Do you think the two standards bodies know that the product of WG21 is just pieces of paper with no idea whether they can be or will be implemented? Or is this all far above what anybody senior at ISO or the IEC understands because they aren't programmers?
Even at W3C you were expected (when I had anything to do with it) to actually build the prototype before you publish the standard, and obviously the IETF's "Rough Consensus and Running Code" speaks to that way of thinking too.
I feel like if ISO 216 claimed you can fold a square 1x1 metre piece of paper in half and preserve the proportions, that wouldn't have survived into a published document. Sure you can write that claim, but you cannot actually make that fold, it's surely amazing that the C++ Committee are not subject to the same consideration and yet here we are.
Even at W3C you were expected (when I had anything to do with it) to actually build the prototype before you publish the standard, and obviously the IETF's "Rough Consensus and Running Code" speaks to that way of thinking too.
I feel like if ISO 216 claimed you can fold a square 1x1 metre piece of paper in half and preserve the proportions, that wouldn't have survived into a published document. Sure you can write that claim, but you cannot actually make that fold, it's surely amazing that the C++ Committee are not subject to the same consideration and yet here we are.
> It is kind of crazy that JTC1 is OK with producing entirely imaginary documents.
I don’t think they do this much if at all any more having been burned in the past. If anything they are more extreme in the other direction: for every person who complains the standard is moving too quickly there is someone complaining that the committee is moving too slowly (“what? Still no networking?”)
They aren’t as hardcore as the IETF’s two independent implementations but I’m not sure how faithful the IETF ever was to that (perhaps apocryphal) criterion anyway.
I don’t think they do this much if at all any more having been burned in the past. If anything they are more extreme in the other direction: for every person who complains the standard is moving too quickly there is someone complaining that the committee is moving too slowly (“what? Still no networking?”)
They aren’t as hardcore as the IETF’s two independent implementations but I’m not sure how faithful the IETF ever was to that (perhaps apocryphal) criterion anyway.
They do reject things based on implementation difficulty too. "Static if considered" rejects it on the basis that the implementations would struggle.
Not really, it had nothing to do with implementation difficulty and the paper actually states that implementing static if would be fairly easy:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n361...
What the paper says is that static if would make it much harder to perform static analysis of source code, not really because it's hard to implement but because the kind of combinatorial explosion introduced by having non-local bifurcating source code branches to analyze makes analysis incredibly slow.
C++ did eventually adopt if constexpr, which does not have this problem since the branches are always local.
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n361...
What the paper says is that static if would make it much harder to perform static analysis of source code, not really because it's hard to implement but because the kind of combinatorial explosion introduced by having non-local bifurcating source code branches to analyze makes analysis incredibly slow.
C++ did eventually adopt if constexpr, which does not have this problem since the branches are always local.
if constexpr is the static if we have at home. It's rubbish.
On the contrary, what is happening is the hard reality of MIT based compilers when downstream doesn't care about improving upstream language compliance.
clang is trailing C++20, since Apple and Google stop caring to be first line contributors.
GCC is actually not that far behind VC++.
And regarding building prototypes, VC++ modules implementation was the prototype.
clang is trailing C++20, since Apple and Google stop caring to be first line contributors.
GCC is actually not that far behind VC++.
And regarding building prototypes, VC++ modules implementation was the prototype.
I’ve shipped two projects wholly in c++20 in the past 4 years with modern practices spanning three platforms (win/Lin/OSX).
No plans to go back to an older standard.
No plans to go back to an older standard.
What does "wholly in C++20" mean? How does "wholly in C++20" differ from "partially in C++20" or just "using C++20"?
Not the author of that comment but I would interpret it to mean all the files were compiled with -std=c++20 (or 2a)
Given the quality and extent of c++20 support over the past few years it can’t have meant using a lot of c++20 at least for most of the time. Then again things like fmt and ranges had 3P libraries that influenced the standard (I’ve been using them myself for years) so more is possible than came with the compilers.
All that being said I would rate the comment as hyperbole. Had it been phrased something like “I’ve been compiling specifying c++20, and have heavily leant on 17 and some key 20 features” I’d be quite fine with it.
Features like coroutines still require a lot of plumbing in order to use; features like that go into a standard so that version n+1 can have the right user abstractions, which can only be developed through experience.
TBH I quite enjoy using C++ from the perspective of a language not based on C (at least don’t think of it that way) with an amazing c-compatibility layer only very occasionally needed. For example I worked on a large system compiled with c++17 at a very high level of abstraction, but that had a deep grotty memory management using pointers, malloc and mmap implemented in two files. It was invisible to the people worrying about the high level logic.
Given the quality and extent of c++20 support over the past few years it can’t have meant using a lot of c++20 at least for most of the time. Then again things like fmt and ranges had 3P libraries that influenced the standard (I’ve been using them myself for years) so more is possible than came with the compilers.
All that being said I would rate the comment as hyperbole. Had it been phrased something like “I’ve been compiling specifying c++20, and have heavily leant on 17 and some key 20 features” I’d be quite fine with it.
Features like coroutines still require a lot of plumbing in order to use; features like that go into a standard so that version n+1 can have the right user abstractions, which can only be developed through experience.
TBH I quite enjoy using C++ from the perspective of a language not based on C (at least don’t think of it that way) with an amazing c-compatibility layer only very occasionally needed. For example I worked on a large system compiled with c++17 at a very high level of abstraction, but that had a deep grotty memory management using pointers, malloc and mmap implemented in two files. It was invisible to the people worrying about the high level logic.
All c++20 here and just waiting for Clang and ultimately Xcode to catch up with MSVC so we can use ranges and pmr
range-v3 is a great library allowing you to bridge the gap: https://github.com/ericniebler/range-v3
Oh nice, it will not require any significant changes for when it does become available!
I see a lot of it in the academic AI world, mostly because as students move from Python (study) to real-world deployments, they need to convert to C++ for performance. Hence, over the past decade I've seen C++ start to look more like a transliteration of Python, and be used that way.
The fact that TensorFlow on Python can use GPUs/TPUs is a no-brainer, but that only works in the server center and not in the field.
The fact that TensorFlow on Python can use GPUs/TPUs is a no-brainer, but that only works in the server center and not in the field.
[deleted]
I wrote C++ at Facebook last year and got to use C++20 features like ranges.
It wasn’t my call, though. Meta has a relatively big C++ infra team that participates in the standards committee, maintains the Folly utility library, and decides how complex new features like coroutines are adopted. On top of that, my code plugged into another team’s system, and they had written their own guidelines on how/if they want to use specific C++ and Folly features.
These guardrails were really useful for a C fossil like me with an on-off relationship to C++… It’s not a terrible language anymore, but it’s even harder than before to find the right subset. At least boost can be finally buried.
It wasn’t my call, though. Meta has a relatively big C++ infra team that participates in the standards committee, maintains the Folly utility library, and decides how complex new features like coroutines are adopted. On top of that, my code plugged into another team’s system, and they had written their own guidelines on how/if they want to use specific C++ and Folly features.
These guardrails were really useful for a C fossil like me with an on-off relationship to C++… It’s not a terrible language anymore, but it’s even harder than before to find the right subset. At least boost can be finally buried.
That's about right in my case. 2019 was more or less the years we switched to C++11. Some projects started using C++11 way earlier, and we still have some code we keep C++98, so, 8 years.
Anyways, I don't know what you are calling "modern" C++, but for me it is C++11 and up. C++11 to C++20 introduced a few major changes but none as pervasive as C++98 to C++11.
Anyways, I don't know what you are calling "modern" C++, but for me it is C++11 and up. C++11 to C++20 introduced a few major changes but none as pervasive as C++98 to C++11.
I've been using C++17 since 2019; C++11 since 2013, and we're starting to scope out upgrading our toolchain to C++20.
Depending on where you work at, my experience suggests 2-5 years for adoption.
Depending on where you work at, my experience suggests 2-5 years for adoption.
We are on the same timeline.
I generally start using -std=c++XX switches in compilers before the standards are actually released ; I don't remember the last time I've seen a project that wasn't at least c++17
LLVM itself has only just now green-lit using c++17 [1] so I find myself using c++14 most of the time.
[1] https://discourse.llvm.org/t/important-new-toolchain-require...
[1] https://discourse.llvm.org/t/important-new-toolchain-require...
You are seriously missing out. C++17 has worked fine for years with clang - and I wouldn't ever go back to writing sfinae code since c++20 concepts are there, it's a massive simplification; likewise for structured bindings (for(auto& [k,v] : map)), if constexpr, ...
I have a habit of modernizing (and functionalizing) C++ codebases in recent jobs I've taken, which tends to fix a lot of memory-related bugs as well as improving performance and readability. When an organization is hidebound in some way, someone has to push to make the change, but it definitely can happen if you can demonstrate the benefits
Windows uses it extensively for both user land system code and the app platform.
Low level languages give you fine control over memory management.
But many companies do not like how the standard library does memory management and they roll their own allocators and libraries that use them.
But many companies do not like how the standard library does memory management and they roll their own allocators and libraries that use them.
You can usually roll your own allocators and use them the standard library.
But one of the nice things about c++ is when you have specialized needs you can write your own implementation of something and it’s just as “first class” as something in std::.
But one of the nice things about c++ is when you have specialized needs you can write your own implementation of something and it’s just as “first class” as something in std::.
This is nice short-hand that I've wanted for a while. I do wish they would have made them overloads of the existing functions in the same namespace, rather than in a new ranges namespace. Oh well, you can always use that namespace, and even if you don't "::ranges" is still less typing than "begin(), end()".
You can always do something like
namespace rng = std::ranges;
namespace rng = std::ranges;
> namespace rng = std::ranges
Aliasing the namespace is great! But pick a good name for the alias. Naming things is, after all, one of the hardest things for programmers to do.
If I see `rng::` without knowing what it is then I'm going to assume it's something to do with a random number generator.
Aliasing the namespace is great! But pick a good name for the alias. Naming things is, after all, one of the hardest things for programmers to do.
If I see `rng::` without knowing what it is then I'm going to assume it's something to do with a random number generator.
I like c++ but it feels maddening to learn. There was a time when I would tell people to learn C++ but now I tell them to start with C and work their way up because if the choice is between C and C++, C has become the more readable language somehow if you don't know what abstract classes, templates, and functional constructs are....even a bubble sort in C++ takes some explaining in terms of just the syntax sugar.
GO and rust are great languages and I hope they go the distance and learn some of the lessons from C and especially C++
GO and rust are great languages and I hope they go the distance and learn some of the lessons from C and especially C++
This is totally backwards advice. If you're going to teach C/C++, it makes far more sense to start with modern c++ which takes care of so much for you. std::string, std::vector, std::unique_ptr, and std::shared_ptr all alone make C++ far more approachable (and readable!) than C. And you can just entirely avoid pointers for a while, avoiding the need to cover things like avoiding returning pointers to stack values until much, much later.
After that you can then peel back the layers and discuss things like manual memory allocations, how vectors work under the covers, etc...
But C is an awful language to start with. It's incredibly complex to actually use and full of sharp edges. The grammar simplicity betrays the extreme mental complexity to actually use it without crashing or leaking memory everywhere. Not to mention the huge overhead in just doing simple things since nothing is included, and nothing is straightforward (like containers like hashmaps - hugely complex in C, trivial as heck in every other language)
And that's before you get into the fact that you can't even just learn C. You have to also learn macros at the same time to actually do anything effectively, which is basically a second language full of its own quirks and problems. With C++ you can reasonably avoid learning macros for a long, long time.
After that you can then peel back the layers and discuss things like manual memory allocations, how vectors work under the covers, etc...
But C is an awful language to start with. It's incredibly complex to actually use and full of sharp edges. The grammar simplicity betrays the extreme mental complexity to actually use it without crashing or leaking memory everywhere. Not to mention the huge overhead in just doing simple things since nothing is included, and nothing is straightforward (like containers like hashmaps - hugely complex in C, trivial as heck in every other language)
And that's before you get into the fact that you can't even just learn C. You have to also learn macros at the same time to actually do anything effectively, which is basically a second language full of its own quirks and problems. With C++ you can reasonably avoid learning macros for a long, long time.
C is more useful to a broader range of programmers than C++. If your goal is to maintain million LOC C++ projects and make that your whole career, then spending the considerable time effort in C++ is worth it. But the whole world speaks C, it's so much simller. If your goal is to wrap existing libraries or speed up a hot spot in a language like python, plain C is a no brainer.
C as an ABI is basically its own thing. And can be implementated in C++ anyway just with 'extern "C"' slapped onto the function.
But it definitely doesn't make sense to start teaching anything at this level with "here's how you design a stable API/ABI". That's a skill set that relatively few need to know
But it definitely doesn't make sense to start teaching anything at this level with "here's how you design a stable API/ABI". That's a skill set that relatively few need to know
C as an ABI is basically its own thing. And can be implementated in C++ anyway just with 'extern "C"' slapped onto the function.
Yeah, so learning C is required to write a portable C++ lib/extension, so you know what can go in `extern "C"` and what can't. At that point, you might as well do the whole thing in C and benefit from the super fast compile times.
But it definitely doesn't make sense to start teaching anything at this level with "here's how you design a stable API/ABI". That's a skill set that relatively few need to know
Fair enough, computing is a big field. For me non GC'd languages are something I dip into for a particular task. The mission is to get in, write the bare minimum, and get out as soon as possible. If I wanted to "move in" as it were, the (substantial!) time investment to master C++ or Rust is probably worth it.
Yeah, so learning C is required to write a portable C++ lib/extension, so you know what can go in `extern "C"` and what can't. At that point, you might as well do the whole thing in C and benefit from the super fast compile times.
But it definitely doesn't make sense to start teaching anything at this level with "here's how you design a stable API/ABI". That's a skill set that relatively few need to know
Fair enough, computing is a big field. For me non GC'd languages are something I dip into for a particular task. The mission is to get in, write the bare minimum, and get out as soon as possible. If I wanted to "move in" as it were, the (substantial!) time investment to master C++ or Rust is probably worth it.
> Yeah, so learning C is required to write a portable C++ lib/extension, so you know what can go in `extern "C"` and what can't. At that point, you might as well do the whole thing in C and benefit from the super fast compile times.
Neither claim there is really true at all. Learning how to write a stable extern C ABI really doesn't require learning C at all, nor even actually using C. Eg, I can put C++ classes in extern C functions just fine, as long as I do so as opaque pointers. Which you need to do for C as well, or use one of the other struct versioning schemes.
And then similarly why would I bother with C's nightmare of data structures or error handling in the implementation when I can use C++ instead and have it be a walk in the park? Marginally faster compile times isn't remotely worth it when you're compiling more often to fix more bugs.
Finally no you don't need C ABI to have a portable C++ library. You only need a C ABI to have a backwards compatible library as a prebuilt (and even that isn't strictly true, see eg libc++), which is a very very small niche within a niche. Like you're only doing that if you're an OS platform. Everyone else just ships C++ APIs and it works great (eg, abseil, folly, boost, skia, etc...)
Neither claim there is really true at all. Learning how to write a stable extern C ABI really doesn't require learning C at all, nor even actually using C. Eg, I can put C++ classes in extern C functions just fine, as long as I do so as opaque pointers. Which you need to do for C as well, or use one of the other struct versioning schemes.
And then similarly why would I bother with C's nightmare of data structures or error handling in the implementation when I can use C++ instead and have it be a walk in the park? Marginally faster compile times isn't remotely worth it when you're compiling more often to fix more bugs.
Finally no you don't need C ABI to have a portable C++ library. You only need a C ABI to have a backwards compatible library as a prebuilt (and even that isn't strictly true, see eg libc++), which is a very very small niche within a niche. Like you're only doing that if you're an OS platform. Everyone else just ships C++ APIs and it works great (eg, abseil, folly, boost, skia, etc...)
We're talking past each other here. When I say "portable" I mean easy to use the resulting lib in non C or C++ languages.
As for why would you bother? I don't know, I guess you wouldn't, because you know C++ really well. I've been paid for it before, know it OK, and at the end of the day I'm more productive in C for the problems I want to drop down to that level for.
As for why would you bother? I don't know, I guess you wouldn't, because you know C++ really well. I've been paid for it before, know it OK, and at the end of the day I'm more productive in C for the problems I want to drop down to that level for.
These days it makes more sense to start from the other end if you ask me, and that has been true for quite a while.
I find that my C++ style has drifted further and further into value land with time, which is a major difference to C where the same style is pretty much impossible to pull off.
From one perspective, the language gets less and less complex; but the flip side is that all the old stuff is still in there and has the potential to cause a lot of trouble if you're not familiar with the details.
Taken as a whole, it's pretty much an impossible language to master and has been for some time.
I find that my C++ style has drifted further and further into value land with time, which is a major difference to C where the same style is pretty much impossible to pull off.
From one perspective, the language gets less and less complex; but the flip side is that all the old stuff is still in there and has the potential to cause a lot of trouble if you're not familiar with the details.
Taken as a whole, it's pretty much an impossible language to master and has been for some time.
> There was a time when I would tell people to learn C++ but now I tell them to start with C and work their way up
I tell people to learn Python. When they get a hang of it then I introduce them to C and pointers. When they can demonstrate effective use of pointers without blowing up then advance to C++. If not then just keep using Python. I'd rather them learn computer science fundamentals on the easy language. Then they can learn the better language out of necessity ("i need more performance" or "i need more control over the data structure in memory" or similar) instead of shoehorning them into a language they're not ready for.
I love C++. But it's not for everyone.
I tell people to learn Python. When they get a hang of it then I introduce them to C and pointers. When they can demonstrate effective use of pointers without blowing up then advance to C++. If not then just keep using Python. I'd rather them learn computer science fundamentals on the easy language. Then they can learn the better language out of necessity ("i need more performance" or "i need more control over the data structure in memory" or similar) instead of shoehorning them into a language they're not ready for.
I love C++. But it's not for everyone.
Genuine question: how do you teach beginners about python's value and reference semantics if they don't know what a pointer is?
When I learned python, I knew a but of C, but was certainly no expert. I remember finding it incredibly confusing that I could pass a list or instance of a class to a function, mutate it, and the caller would see that mutation, but the same did not hold for say a float. The only way I could make sense of it was to mentally classify certain types of objects as "getting secretly passed by pointer", and others as getting evidently passed by value. Without at least a familiarity with C, I think that would have been much harder to understand.
When I learned python, I knew a but of C, but was certainly no expert. I remember finding it incredibly confusing that I could pass a list or instance of a class to a function, mutate it, and the caller would see that mutation, but the same did not hold for say a float. The only way I could make sense of it was to mentally classify certain types of objects as "getting secretly passed by pointer", and others as getting evidently passed by value. Without at least a familiarity with C, I think that would have been much harder to understand.
> how do you teach beginners about python's value and reference semantics
The great thing about Python is that it's super easy to learn by example without having to troubleshoot cryptic compiler errors first. So show them a few objects. Modify those objects. Show them how to deep-copy objects and how to modify objects by reference without a deep-copy.
Once the examples have been made then start asking about how they might write their own, in Python, types that could be deep-copied or reference-modified.
Make sure to include your own questions about classes, class attributes, function parameters, initialization, and forced cleanup using either `del` or `with` -- it's handy to use a file object for examples of object destruction since that's buffered and so writes to it won't show up until it's flushed or closed (which occurs automatically when the file object is destroyed).
Then you might expand to questions like: if you have a property somewhere that points to "some reference" but the reference could change to one of several different objects or maybe even to none of the objects, how would you do that? Is the property maybe pointing to one of the other objects? There are many ways to do this and most of them are "valid" for mentoring. What are some other ways to do it and what are some of pitfalls or benefits to the other ways?
From there you can segue your way into describing what a pointer is "under the hood" if you think the student is ready for more info about pointers.
The great thing about Python is that it's super easy to learn by example without having to troubleshoot cryptic compiler errors first. So show them a few objects. Modify those objects. Show them how to deep-copy objects and how to modify objects by reference without a deep-copy.
Once the examples have been made then start asking about how they might write their own, in Python, types that could be deep-copied or reference-modified.
Make sure to include your own questions about classes, class attributes, function parameters, initialization, and forced cleanup using either `del` or `with` -- it's handy to use a file object for examples of object destruction since that's buffered and so writes to it won't show up until it's flushed or closed (which occurs automatically when the file object is destroyed).
Then you might expand to questions like: if you have a property somewhere that points to "some reference" but the reference could change to one of several different objects or maybe even to none of the objects, how would you do that? Is the property maybe pointing to one of the other objects? There are many ways to do this and most of them are "valid" for mentoring. What are some other ways to do it and what are some of pitfalls or benefits to the other ways?
From there you can segue your way into describing what a pointer is "under the hood" if you think the student is ready for more info about pointers.
That's not how Python works so trying to map it onto value/reference categories actually leads you astray. There is no pass by value, all objects are shared between caller and callee. But since a float is immutable, there is no internal state you can change that can be observed by the caller. If you do x += y, i.e x = x.__iadd__(y), the distinction is actually between immutable objects where iadd returns a new object, and mutable objects, where iadd modifies x and then returns x.
> That's not how Python works so trying to map it onto value/reference categories actually leads you astray
You cannot teach physics to five year olds by, for example, starting with Euler's equations.
Python doesn't work the same way as C, sure. But it works fine enough to get a feeling for how something "might" work. Then when they move on to another language, just as graduating to a harder class, you might have to un-learn some of the things to learn how it's really done.
You cannot teach physics to five year olds by, for example, starting with Euler's equations.
Python doesn't work the same way as C, sure. But it works fine enough to get a feeling for how something "might" work. Then when they move on to another language, just as graduating to a harder class, you might have to un-learn some of the things to learn how it's really done.
You teach them how it works in Python. You don't take a detour to an entire other language.
Even as a polyglot that picks up new languages quickly and often, I think this is true of most actively maintained major languages now.
We’re in an age where major languages are expected to cross-pollinate: if there’s a cool paradigm or technique in some other major language, how do we evolve our language to support it?
That’s not a terrible thing in itself, but it means that most major languages are multi-paradigm now and become more so every release.
As a consequence, learning becomes less straightforward.
C may feel like a nice starter to you specifically because it’s been comparatively resistant to this trend. It’s got a ton of tricks to learn, but there are only a few paths through learning it.
We’re in an age where major languages are expected to cross-pollinate: if there’s a cool paradigm or technique in some other major language, how do we evolve our language to support it?
That’s not a terrible thing in itself, but it means that most major languages are multi-paradigm now and become more so every release.
As a consequence, learning becomes less straightforward.
C may feel like a nice starter to you specifically because it’s been comparatively resistant to this trend. It’s got a ton of tricks to learn, but there are only a few paths through learning it.
C takes on many dialects based on specialization. Compare code from the following, and you will see a range from trivial to understand to WTF. These are all real-world applications:
- Linux kernel (events) - https://github.com/torvalds/linux/blob/master/kernel/events/...
- Arm CMSIS - (16-bit math) - https://github.com/ARM-software/CMSIS_5/blob/develop/CMSIS/D...
- Numerical Methods in C - (Jacobian FP) - https://github.com/saulwiggin/Numerical-Recipies-in-C/blob/m...
- GNU 'ls' Command - https://github.com/coreutils/coreutils/blob/master/src/ls.c
- Gstreamer - (De-facto media streaming) - https://github.com/GStreamer/gstreamer/blob/master/gst/gstel...
GStreamer is my favorite because it basically creates VTables like C++ but calls them Klasses (based on Gnome), and it is just a brilliant framework in general, but an utter perversion of C IMHO.
- Linux kernel (events) - https://github.com/torvalds/linux/blob/master/kernel/events/...
- Arm CMSIS - (16-bit math) - https://github.com/ARM-software/CMSIS_5/blob/develop/CMSIS/D...
- Numerical Methods in C - (Jacobian FP) - https://github.com/saulwiggin/Numerical-Recipies-in-C/blob/m...
- GNU 'ls' Command - https://github.com/coreutils/coreutils/blob/master/src/ls.c
- Gstreamer - (De-facto media streaming) - https://github.com/GStreamer/gstreamer/blob/master/gst/gstel...
GStreamer is my favorite because it basically creates VTables like C++ but calls them Klasses (based on Gnome), and it is just a brilliant framework in general, but an utter perversion of C IMHO.
The Linux kernel does the same thing as Gstreamer with file operations etc, I r thought it pretty neat, not really a perversion at all.
I didn't know that. Cool. Also, I was being silly, because for some reason it took me a while to get my head around klass, and compared to my other listed samples, it is an oddball.
[deleted]
Even with C it only looks like it, if one sticks mainly with a specific compiler and OS.
If what you need is C++ (which IMNSHO it is not) then starting with C is a bad idea. Here's Kate Gregory's talk, you should definitely listen to her even if you think I'm an idiot because she actually teaches people C++ and I (thankfully) do not.
https://www.youtube.com/watch?v=YnWhqhNdYyk
Now here's my rant, which is unrelated to Kate's very smart talk:
C has an excuse, because it was written in the 1970s for the PDP-11. In the 1970s struct qualifies as a fancy new feature. In the 1970s a wide pointer is very expensive. In the 1970s a linked list is often a good choice of data structure. C++ comes along quite a lot later. These things are already untrue or fast becoming untrue, but rather than risk being unpopular Bjarne's language just cargo cults C. It is almost all of C, plus more... stuff.
C++ does not fix any of the worst problems with C, because doing so would risk losing compatibility and hurt Bjarne's adoption story. As a result, with only a handful of exceptions all of that broken garbage is still there. C++ still has the almost useless built-in array type from C, it keeps weird syntax from C that was too hard to ban in the 1970s compiler but you should never use, its built-in types have the same stupid, confusing names like "long" and "double", it has this awful "macro pre-processor" which makes even trivial tooling problems very difficult and set back software quality by at least a decade.
Kate's approach avoids teaching beginners about most of this. It's still there, which is bad, but at least you aren't making them learn about it, only to them immediately tell them it's forbidden knowledge and is prohibited in your nice modern C++ codebase. Instead of starting with raw pointers, and then trying to impress upon them later that these are a bad idea, Kate gets to begin with references and then a smart owning pointer.
https://www.youtube.com/watch?v=YnWhqhNdYyk
Now here's my rant, which is unrelated to Kate's very smart talk:
C has an excuse, because it was written in the 1970s for the PDP-11. In the 1970s struct qualifies as a fancy new feature. In the 1970s a wide pointer is very expensive. In the 1970s a linked list is often a good choice of data structure. C++ comes along quite a lot later. These things are already untrue or fast becoming untrue, but rather than risk being unpopular Bjarne's language just cargo cults C. It is almost all of C, plus more... stuff.
C++ does not fix any of the worst problems with C, because doing so would risk losing compatibility and hurt Bjarne's adoption story. As a result, with only a handful of exceptions all of that broken garbage is still there. C++ still has the almost useless built-in array type from C, it keeps weird syntax from C that was too hard to ban in the 1970s compiler but you should never use, its built-in types have the same stupid, confusing names like "long" and "double", it has this awful "macro pre-processor" which makes even trivial tooling problems very difficult and set back software quality by at least a decade.
Kate's approach avoids teaching beginners about most of this. It's still there, which is bad, but at least you aren't making them learn about it, only to them immediately tell them it's forbidden knowledge and is prohibited in your nice modern C++ codebase. Instead of starting with raw pointers, and then trying to impress upon them later that these are a bad idea, Kate gets to begin with references and then a smart owning pointer.
Struct was already a feature in Jovial in 1958, but I digress.
Plenty of very hard 1970's features at Bell Labs, weren't a problem at IBM, DEC, Xerox, Olivetti,....
As for the way C compatibility taints C++, I agree, however Bjarne made juice with the lemons he had, and if it is to do a Python 3 in the C++ world, then most would rather migrate to Rust than use such C incompatible C++.
Plenty of very hard 1970's features at Bell Labs, weren't a problem at IBM, DEC, Xerox, Olivetti,....
As for the way C compatibility taints C++, I agree, however Bjarne made juice with the lemons he had, and if it is to do a Python 3 in the C++ world, then most would rather migrate to Rust than use such C incompatible C++.
Why wouldn't they just use the older version of C++? If you don't want non-c compatible c++ you could just stick to C++20 instead of upgrading to "C++breaking_changes".
I ask because its not like support will ever be phased out like Python 2.
I ask because its not like support will ever be phased out like Python 2.
A language isn't used alone, it depends on an ecosystem, and people that care to keep old compilers going.