r/wg21
P3856R4 - New reflection metafunction - is_structural_type WG21
Posted by u/reflection_paper_feed · 6 hr. ago

Document: P3856R4
Authors: Jagrut Dave, Alisdair Meredith
Date: 2026-01-17
Audience: LEWG/LWG

Addresses US NB comment 49. The standard uses "structural type" in several places (NTTPs, std::array) and library mandates require it, but there's no way to query whether a type is structural. This paper adds is_structural_type(info) as a reflection metafunction and std::is_structural<T> as a type trait. Comes with a proof-of-concept implementation on Bloomberg's Clang fork using P2996 reflection.

▲ 42 points (92% upvoted) · 8 comments
sorted by: best
u/nttp_power_user 34 points 5 hr. ago

It's wild that we've had structural types since C++20 NTTPs and there's been no way to check at compile time whether a type qualifies. Library code that wants to wrap values as NTTPs has been guessing. The motivating example with const_wrapper is exactly the pattern I've wanted - SFINAE-friendly selection between NTTP path and runtime path based on whether the type is structural.

u/reflection_metafunction_fan 28 points 5 hr. ago

Section 4 on type traits vs metafunctions is a valuable discussion beyond the scope of this paper. Should is_structural<T> and is_structural_type(^^T) be independent implementations or should one wrap the other? The paper argues independence - different paradigms, different side effects, different error handling. That seems right.

u/poc_implementation_reader 22 points 4 hr. ago

The proof of concept is interesting because it shows what P2996 reflection can and can't do. It can check public/non-mutable/structural recursively. It can't query "is this function constexpr" or "is this a lambda closure type" - so the literal type check is conservative. The paper identifies these as gaps that future metafunctions should fill.

u/bloomberg_cpp_watcher 16 points 4 hr. ago

Bloomberg papers tend to be focused and implementable. Two authors, one metafunction, one type trait, proof of concept on their Clang fork. This is what a good NB comment resolution looks like.

u/is_literal_type_rip 12 points 3 hr. ago

Section 3.3 notes that std::is_literal_type was removed in C++20 and there's no reflection replacement. The paper's implementation has to work around this absence. Feels like we removed a useful trait and never replaced it.

u/r4_cleanup 8 points 2 hr. ago

R4 removed is_destructurable_type per LEWG feedback and dropped the access context parameter from the signature. Clean scoping - one concept, one metafunction, one trait. Ship it.

u/godbolt_link_required 5 points 1 hr. ago

The paper includes a Godbolt link to the proof of concept. You can actually run the static_asserts. More papers should do this.