std::ranges::in_in_result(3)

๐Ÿ“ฆ version 2024.07.05, in nixpkgs unstable, opensuse-leap 16.0

okay bestie, buckle up: this is the manual page for std::ranges::in_in_result(3) from the C++ Standard Libary, and it's lowkey one of the cutest little aggregate structs in the whole ranges game. ๐Ÿซถโœจ

๐Ÿ’– NAME ๐Ÿ’–

std::ranges::in_in_result โ€” literally the class template named in the title. The NAME section is std::ranges::in_in_result - std::ranges::in_in_result, so yes: same name, same energy, no cap. ๐Ÿ’…

โœจ Synopsis โœจ

Here's the quick vibe check, bestie:

Defined in header <algorithm>
template< class I1, class I2 >  (since C++20)
struct in_in_result;

ranges::in_in_result is a class template that provides a way to store two iterators as a single unit. ๐Ÿฆ‹

This class template has no base classes or declared members other than those shown below. Thus it is suitable for use with structured bindings. Periodt.

All special member functions of this class template are implicitly declared, which makes specializations be aggregate classes, and propagate triviality, potentially-throwing-ness, and constexpr-ness of corresponding operations on data members. It's giving very "compiler does the boring parts, you get the cute bundle" energy. โœจ

๐Ÿงš Template parameters ๐Ÿงš

  • I1, I2 โ€” the types of the iterators that ranges::in_in_result stores. ๐Ÿ’–

๐ŸŽ€ Data members ๐ŸŽ€

  • Member name: in1 โ€” Definition: a value (that is supposed to be an iterator) of type I1. (public member object)
  • Member name: in2 โ€” Definition: a value (that is supposed to be an iterator) of type I2. (public member object)

All these members are declared with [[no_unique_address]] attribute. Slay, no wasted bytes bestie. ๐ŸŽ€

๐Ÿ’œ Member functions ๐Ÿ’œ

โœจ std::ranges::in_in_result::operator in_in_result<II1, II2> โœจ

template<class II1, class II2>
requires std::convertible_to<const I1&, II1> &&
         std::convertible_to<const I2&, II2>
constexpr operator in_in_result<II1, II2>() const &;

template<class II1, class II2>
requires std::convertible_to<I1, II1> &&
         std::convertible_to<I2, II2>
constexpr operator in_in_result<II1, II2>() &&;

Converts *this to the result by constructing every data member of the result from the corresponding member of *this. Obsessed with the directness, honestly. ๐Ÿ’…

  1. (1) Equivalent to return {in1, in2};.
  2. (2) Equivalent to return {std::move(in1), std::move(in2)};.

๐ŸŒˆ Standard library ๐ŸŒˆ

The following standard library functions use ranges::in_in_result as the return type:

๐Ÿงฎ Algorithm functions ๐Ÿงฎ

  • ranges::mismatch โ€” finds the first position where two ranges differ. (C++20) (niebloid)
  • ranges::swap_ranges โ€” swaps two ranges of elements. (C++20) (niebloid)

๐ŸŒธ Synopsis, again ๐ŸŒธ

okay here's the full code-block moment, bestie โ€” same facts, now in maximum iconic form:

namespace std::ranges
{
    template<class I1, class I2>
    struct in_in_result
    {
        [[no_unique_address]] I1 in1;
        [[no_unique_address]] I2 in2;

        template<class II1, class II2>
        requires std::convertible_to<const I1&, II1> &&
                 std::convertible_to<const I2&, II2>
        constexpr operator in_in_result<II1, II2>() const &
        {
            return {in1, in2};
        }

        template<class II1, class II2>
        requires std::convertible_to<I1, II1> &&
                 std::convertible_to<I2, II2>
        constexpr operator in_in_result<II1, II2>() &&
        {
            return {std::move(in1), std::move(in2)};
        }
    };
}

๐Ÿฆ‹ Notes ๐Ÿฆ‹

Each standard library algorithm that uses this family of return types declares a new alias type, e.g. using merge_result = in_in_out_result<I1, I2, O>;. ๐Ÿฆ‹

The names for such aliases are formed by adding the suffix "_result" to the algorithm's name. So, the return type of std::ranges::merge can be named as std::ranges::merge_result. iykyk.

Unlike std::pair and std::tuple, this class template has data members of meaningful names. That's the whole point and honestly? We love a communicative queen. ๐Ÿ‘‘

๐Ÿ“ Example ๐Ÿ“

// Run this code

#include <algorithm>
#include <iostream>
#include <ranges>

int main()
{
    constexpr static auto in1 = {1, 2, 3, 4};
    constexpr static auto in2 = {1, 2, 4, 5};

    constexpr auto result {std::ranges::mismatch(in1, in2)};

    static_assert(2 == std::ranges::distance(in1.begin(), result.in1));
    static_assert(2 == std::ranges::distance(in2.begin(), result.in2));
}

โญ See also โญ

  • pair โ€” implements binary tuple, i.e. a pair of values. (class template)
  • tuple โ€” implements fixed size container, which holds elements of possibly different types. (C++11) (class template)

okay that's the whole page, bestie ๐Ÿ’– source: http://cppreference.com, version/date: 2024.06.10, page: std::ranges::in_in_result(3). mwah ๐Ÿ’‹๐Ÿ’…

๐Ÿ“ฆ where this page comes from