C++ Logo

std-proposals

Advanced search

Re: [std-proposals] opt-in inheritable friendship

From: Arthur O'Dwyer <arthur.j.odwyer_at_[hidden]>
Date: Thu, 22 Oct 2026 16:51:17 -0400
On Thu, Oct 22, 2026 at 3:20 PM Theoden Cook via Std-Proposals <
std-proposals_at_[hidden]> wrote:

> I have an idea for a potential C++ language feature. I'd appreciate
> feedback on whether it would be worth pursuing as a proposal.
> *The idea: opt-in inheritable friendship*
> Currently in C++, friendship is neither inherited nor transitive. If a
> class is declared as a friend of another class, its derived classes do not
> inherit that friendship.
> I'd like to propose an opt-in mechanism that allows a class to explicitly
> declare a friendship relationship as inheritable.
>
> For example, the syntax could look similar to this:
>
> class A {
> [[inheritable]] friend class B;
>
>
(1) Personally, I don't think this idea has the requisite "bang for the
buck." I've never wanted such a feature myself; in fact I tend to say that
the `friend` keyword *in general* is a code smell, except when it's used
*specifically* for the hidden friend idiom.
(Note that despite that position, I was a coauthor/supporter on, although
not the originator of, P2893 Variadic Friends
<https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2024/p2893r3.html>,
adopted for C++26. I do like consistency in the language, even in parts
you probably shouldn't use.)

(2) This definitely isn't the sort of thing you should express with an
[[attribute]].

(3) There's nothing particularly special about *inheritance relationships
in particular*. It looks to me like what you really want is more like

    class A {
      fantasy-template<class T> requires std::derived_from<T, B> friend T;
// not a friend, but a template for stamping out friends
    };

Except that unfortunately `template<~~~> friend ~~~` already has a
different meaning
<https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2024/p2893r3.html#not-for-stamping>
!
But that's the kind of syntax you *want*, so that you can use this same
syntax to express things unrelated to inheritance, like
    fantasy-template<class T> requires requires { typename
T::enable_friendship; } friend T; // befriend any class type that supplies
a member typedef named `enable_friendship`
and
    fantasy-template<class T> friend std::vector<T*>; // befriend
vector<U> when U is a pointer type, and otherwise don't
and so on.

my $.02,
Arthur

Received on 2026-10-22 20:51:36