C++ Logo

std-proposals

Advanced search

Re: [std-proposals] Safer API for minmax with friends?

From: Ell <ell_se_at_[hidden]>
Date: Thu, 6 Mar 2025 23:55:53 +0200
On 3/6/25 12:23, Robin Savonen Söderholm via Std-Proposals wrote:
> Hi!
>
> I recently got burned by a piece of innocent looking code that was
> something along the lines of this:
> ```c++
> auto [min, max] = std::minmax(a, b - a);
> ```
> The problem stems from the fact that std::minmax (not initialiser_list
> api) returns a std::pair<T const&, T const&> regardless of what the
> arguments are AND that the structural bindings 'auto' is just making
> sure that the object being separated is not a reference, NOT that the
> objects inside [...] are not references...
> In the best of worlds I would argue that `auto [x, y] = ...` would mean
> that `x` and `y` are pure values, but I guess such a change could cause
> trouble due to breaking currently working code that relies on the
> reference capture (and it would complicate the meaning of `auto& [x, y]
> = ...`).
> A simpler option would be to change the API for the minmax function (and
> perhaps other, similar looking functions) to something where if an
> RValue is detected amongst the arguments, it would return a std::pair<T,
> T> only (or pair<T const, T const>), while if all arguments are lvalue
> references it could keep it's current form (for speed or for the need of
> testing the address of an argument or something..)
>
> What would be the best remedy for things like this you think?
>

This was discussed on reddit recently [1]. As noted there, the problem
is broader than just dangling references to temporaries. The presence of
unintended references is itself an issue:

    auto [min, max] = std::minmax (x, y); // x and y are lvalues
    std::swap (x, y); // oops, also swaps min and max

I'd be wary of special-casing just the rvalue-argument case.

[1]
https://old.reddit.com/r/cpp/comments/1j2139v/c_creator_calls_for_action_to_address_serious/mfornic/

Received on 2025-03-06 21:56:06