June 30th, 2024

Reflection for C++26

The P2996R4 document proposes a reduced set of static reflection features in C++26, using constant expressions, a reflection operator, metafunctions, and splicers. Implementation progress is ongoing by Lock3 and EDG.

Read original articleLink Icon
Reflection for C++26

The document P2996R4 dated 2024-06-26 proposes a reduced set of features for static reflection in C++26. It suggests using constant expressions to produce reflection values of an opaque type std::meta::info, a reflection operator (^), consteval metafunctions, and splicers to generate grammatical elements from reflections. The proposal aims to facilitate code generation based on program structure observations, known as reflective metaprogramming. It emphasizes starting with a smaller feature set to expedite inclusion in the language, with plans for future enhancements. Notable additions include metafunctions for synthesizing simple struct and union types. The document defends the use of a single opaque reflection type to avoid constraining language evolution and implementation advantages. Implementation status indicates ongoing work by Lock3 and EDG, with available implementations on Compiler Explorer. The implementations cover significant features proposed, including namespace and template splicers, with examples showcased in both implementations. However, some language features like expansion statements are not yet included.

Link Icon 21 comments
By @lallysingh - 4 months
Wow this got really long. I was one of the coauthors for a reflection proposal (N3340) over a dozen years ago. Implementing compile-time reflection is honestly trivial - you basically transfer data from the symbol table on-demand into template specializations. It was roughly 1500 LOC to modify g++ to do it.

Looking at the examples (https://isocpp.org/files/papers/P2996R4.html#examples) what really stands out is the direct integration of type-syntax into the language. It fits in with a certain token-substitution way that connects back to templates. It also replaces some of the uglier operators (typeof?).

I hope it goes int! During the language's stagnation I left for a while, perhaps it'll be competitive again soon.

By @qalmakka - 4 months
While I love this paper and this proposal in general, as a C++ developer every time C++ adds a new major feature I get somewhat worried about two things:

1. how immense the language has become, and how hard it got to learn and implement

2. how "modernising" C++ gives developers less incentives to convince management to switch to safer languages

While I like C++ and how crazy powerful it is, I also must admit decades of using it that teaching it to new developers has become immensely hard in the last few years, and the "easier" inevitably ends up being the unsafe one (what else can you do when the language itself tells you to refrain from using `new`?).

By @w4rh4wk5 - 4 months
Do I understand correctly that this proposal does not include annotations (i.e. attributes).

More specifically, with this I can iterate over struct members and get their names and types, but I cannot attach additional information to these members, like whether they should be serialized or under which name.

The referenced proposal P1887R1 covers this, but that's not included here, right?

P1887R1: https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2020/p18...

By @stefanos82 - 4 months
Can I ask a naive question that consists of two parts and please don't flame me? lol

  * What type of problems static reflection could solve, in general?
  * Are there specific cases and / or situations where static reflection could resolve such case, even simplify an unnecessary complexity?
By @gpderetta - 4 months
I have been waiting for static reflection for the last 20 years. The current proposal seems quite nice, but the real question is whether any non trivial usage will kill compilation performance.
By @TillE - 4 months
Finally. I think there have been proposals since C++17 at least, and all I really wanted is for them to solve the common problem of basic static reflection for enums (without hacks like magic_enum uses).
By @ahartmetz - 4 months
This looks surprisingly fine! The opaque, extensible types remind me of Win32 with its extensibility through ever new message types. The syntax looks better than expected, too - well, it's better than templates...
By @bingo3131 - 4 months
FYI: this is the latest draft of the proposal and it has not been voted into C++26 yet, but it is getting close.
By @pjmlp - 4 months
Note that there are links pointing to examples on Compiler Explorer, using the EDG and clang preview implementations.
By @guardian5x - 4 months
With every new C++ feature, I can't help to think "Oh yea, cause C++ isn't complicated enough"
By @tempodox - 4 months
Highly interesting, I'm looking forward to this.

But the `member_number` functions in § 3.2 look disturbing to me. It's not discernible how invalid arguments are handled. Normally I'd look at generated assembly to answer a question like that, but this probably doesn't make sense with compile-time-fu (`constexpr`)…

By @flykespice - 4 months
Has finally the committee come to reflection after decades of standard revisions and footguns? /j
By @Dwedit - 4 months
Compile time or runtime? Compile time reflection would be completely painless and bloat-free.
By @kstrauser - 4 months
I haven't touched C++ since undergrad. Neither have I written any Qt code. But from memory, doesn't Qt's moc implement some of this stuff because it wasn't available in C++? Could this replace moc?
By @account42 - 4 months
I'm not convinced that wasting a simple clean syntax (prefix unary ^) is warranted for something that should be rare outside of a few libraries.
By @forrestthewoods - 4 months
I'm surprised at the positive response in this thread. I find the syntax of this beyond atrocious! My goodness C++ really does not know how to do anything simply does it?
By @huhtenberg - 4 months
Oi vey. Poor C++. Look how they massacred my boy.
By @raymond_goo - 4 months
Ctrl-F "networking", cry, close page...

See also: https://github.com/cplusplus/networking-ts

By @SilverSlash - 4 months
How about: Deprecation for C++26?