Date: Sun, 13 Apr 2025 14:21:08 +0200
niedz., 13 kwi 2025 o 13:41 Henning Meyer via Std-Proposals
<std-proposals_at_[hidden]> napisaĆ(a):
>
> I believe there are many custom implementations of std::function and
> std::any with a small buffer optimization in production code bases, just
> as there are many hash map implementations. And std::expected-clones for
> code bases not yet fully converted to C++23. From a semantics
> perspective, std::expected<R,E> is quite different from
> std::variant<R,E>, but from a tooling perspective they pose the same
> problem of finding out which state the variable is in and how to get the
> contained object.
>
This is why I like Herb `as` and `is` proposal as it creates one "api"
for all types like this.
> On 13.04.25 11:43, Frederick Virchanza Gotham via Std-Proposals wrote:
> >
> >
> > On Saturday, April 12, 2025, Henning Meyer wrote:
> >
> >
> > I would like to work generically with std::variant and std::any.
> >
> >
> >
> > Not particularly relevant to this topic, but I think two or three
> > years ago I wrote a class that is kind of halfway between 'variant'
> > and 'any'. Basically you had all the benefits of 'any' except that it
> > didn't dynamically allocate. So you had to specify a maximum size for
> > the object, sort of like:
> >
> > template<size_t N = 256zu>
> > class any_variant {
> > constexpr std::size_t N = N;
> > alignas(max_align_t) byte buf[N];
> > type_info const *pti = nullptr;
> > void (*destructor)(void*) noexcept = nullptr;
> > };
> >
> > The best thing about it was that you got a compiler error (rather than
> > a runtime error) if you tried to host an object that didn't fit, like
> > this:
> >
> > template<typename Tref>
> > constexpr any_variant &operator=(Tref &&arg)
> > noexcept(noexcept(remove_cvref_t<Tref>(Tref&&)))
> > {
> > static_assert( N >= sizeof arg );
> >
> > if ( destructor )
> > {
> > destructor(buf); // better not throw
> > destructor = nullptr;
> > pti = nullptr;
> > }
> >
> > typedef remove_cvref_t<Tref> T;
> >
> > construct_at<T>( (T*)buf, forward<Tref>(arg) );
> > pti = &typeid(T);
> > destructor = +[](void *const arg) noexcept
> > {
> > ((T*)arg)->~T(); // better not throw
> > };
> > }
> >
> > Might need compiler support to make it 'constexpr' because I cast a
> > void* to a T*.
> >
> >
> >
> >
> >
> --
> Std-Proposals mailing list
> Std-Proposals_at_[hidden]
> https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals
<std-proposals_at_[hidden]> napisaĆ(a):
>
> I believe there are many custom implementations of std::function and
> std::any with a small buffer optimization in production code bases, just
> as there are many hash map implementations. And std::expected-clones for
> code bases not yet fully converted to C++23. From a semantics
> perspective, std::expected<R,E> is quite different from
> std::variant<R,E>, but from a tooling perspective they pose the same
> problem of finding out which state the variable is in and how to get the
> contained object.
>
This is why I like Herb `as` and `is` proposal as it creates one "api"
for all types like this.
> On 13.04.25 11:43, Frederick Virchanza Gotham via Std-Proposals wrote:
> >
> >
> > On Saturday, April 12, 2025, Henning Meyer wrote:
> >
> >
> > I would like to work generically with std::variant and std::any.
> >
> >
> >
> > Not particularly relevant to this topic, but I think two or three
> > years ago I wrote a class that is kind of halfway between 'variant'
> > and 'any'. Basically you had all the benefits of 'any' except that it
> > didn't dynamically allocate. So you had to specify a maximum size for
> > the object, sort of like:
> >
> > template<size_t N = 256zu>
> > class any_variant {
> > constexpr std::size_t N = N;
> > alignas(max_align_t) byte buf[N];
> > type_info const *pti = nullptr;
> > void (*destructor)(void*) noexcept = nullptr;
> > };
> >
> > The best thing about it was that you got a compiler error (rather than
> > a runtime error) if you tried to host an object that didn't fit, like
> > this:
> >
> > template<typename Tref>
> > constexpr any_variant &operator=(Tref &&arg)
> > noexcept(noexcept(remove_cvref_t<Tref>(Tref&&)))
> > {
> > static_assert( N >= sizeof arg );
> >
> > if ( destructor )
> > {
> > destructor(buf); // better not throw
> > destructor = nullptr;
> > pti = nullptr;
> > }
> >
> > typedef remove_cvref_t<Tref> T;
> >
> > construct_at<T>( (T*)buf, forward<Tref>(arg) );
> > pti = &typeid(T);
> > destructor = +[](void *const arg) noexcept
> > {
> > ((T*)arg)->~T(); // better not throw
> > };
> > }
> >
> > Might need compiler support to make it 'constexpr' because I cast a
> > void* to a T*.
> >
> >
> >
> >
> >
> --
> Std-Proposals mailing list
> Std-Proposals_at_[hidden]
> https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals
Received on 2025-04-13 12:21:25