11 comments

[ 46.4 ms ] story [ 914 ms ] thread
C++ people are great at making problems for themselves and then solving them to no end.

This does not look like a productive way to get things done.

This is so on-brand for C++, whether that is a blessing or curse is left up to the reader.
To be clear we are — in the service of speed — trying to bake data into compiled program output binaries, which is ostensibly faster because code-pages in memory when executed by CPU as instructions already have it?
The point of the article and of define_static_array is to convert stuff like constexpr std::vector to constexpr std::array.

New (and delete) can be used in constexpr functions, however memory "allocated" like that cannot leave the constexpr "sandbox" so to speak, therefore std::vector cannot be generated at compile-time, but std::array may.

If you are working with fixed-size data like LUTs, just use std::array [1]

[1] Make sure not to use std::to_array when embedding 200KB+ files, as it's a mere constexpr function and not a language construct and will exceed constexpr limits; either specify the size or use a C-style array in this case

> Think of constexpr evaluation as taking place "in the compiler’s imagination."

This is a great line.

constexpr and std::execution seem like neat ideas, maybe I'll give them a shot if I build an AI harness around the compiler so it doesn't make me feel like a hopeless idiot for trying new things.

The problem isn't so much that you feel like an idiot, at least at the time, but that you may think you're a genius and yet actually what you wrote was nonsense and the C++ compiler was under no obligation to tell you about that, indeed in many cases it's forbidden from doing so.

The standard does require that if work was done at compile time the compiler is supposed to tell you if that was nonsense but (a) actually C++ is so complicated your compiler likely has many bugs in this respect and (b) you probably aren't sure the compiler did the work you expected at compile time, knowing all the excuses requires considerable expertise.

I'd recommend you'd give D a try. It manages to have a bunch of the cool features C++ has, while still largely feeling like working in C with some of the cruft fixed.

D's equivalent to "constexpr" is "compile time function evaluation". i.e. in any context where it only makes sense to run code at compile time, it will do so. This makes it trivial to do some pretty complex things at compile time. I put together an example that shows creating static arrays, dynamic arrays, and a dynamic array with a partial fibbonaci sequence all at compile time[0].

[0] https://gist.github.com/SuperDoxin/d9fcc68b73c035cbde7f0bd08...

Would the PMR variants of the STL datatypes be a solution here? The compiler could fill in the details of the range in question (the ro section), and give you constexprness?
Let's try this:

    constexpr std::vector<int> f() { return {1,2,3}; }
    constinit std::vector<int> p = f(); // error
in D!

    const(int)[] f() { return [1,2,3]; }
    immutable int[] aaa = f();
And the object file, look ma, aaa[] is statically allocated:

    internal:
        db      001h,000h,000h,000h,002h,000h,000h,000h ;........
        db      003h,000h,000h,000h,000h,000h,000h,000h ;........
    __D5test63aaayAi:
        db      003h,000h,000h,000h,000h,000h,000h,000h ;........
        db      000h,000h,000h,000h,000h,000h,000h,000h ;........
I love how to do anything in this language, you have to fight it with all you have. You have to use features in ways that feel like they were probably never intended to be used in. Everything is just an accident, some random pattern randomly discovered by someone when some typo happened to compile.