有没有办法轻松处理返回std :: pairs的函数?

Ada*_*adi 33 c++ tuples minmax c++11 std-pair

C++ 11具有std::minmax_element返回一对值的函数.然而,这对于处理和读取来说是相当混乱的,并且产生一个额外的,后来无用的变量来污染范围.

auto lhsMinmax = std::minmax_element(lhs.begin(), lhs.end());
int &lhsMin = *(lhsMinMax.first);
int &lhsMax = *(lhsMinmax.second);
Run Code Online (Sandbox Code Playgroud)

有一个更好的方法吗?就像是:

int lhsMin;
int lhsMax;
std::make_pair<int&, int&>(lhsMin, lhsMax).swap(
    std::minmax_element(lhs.begin(), lhs.end()));
Run Code Online (Sandbox Code Playgroud)

Jar*_*d42 32

使用C++ 1z的结构化绑定,您可以直接执行

auto [lhsMinIt, lhsMaxIt] = std::minmax_element(lhs.begin(), lhs.end());
Run Code Online (Sandbox Code Playgroud)

  • Upvoted,因为它是一个有趣的讨论点,并且_will_是一个很好的解决方案,但这实际上没有回答问题(这是关于C++ 11). (9认同)
  • 整齐!你能在一行中从迭代器对中获取值对吗? (2认同)
  • @AdamHunyadi:C++ 1z是C++ 17的"它还没有正式存在"这个名字,就像C++ 0x如何成为C++ 11(后期!)和C++ 1y因为C++ 14 . (2认同)
  • @LightnessRacesinOrbit:"C++ 1z"后的标准是什么?`C++ 2 {`?:-) (2认同)

krz*_*zaq 23

为避免污染范围,可以将赋值括在较小的范围内:

int lhsMin, lhsMax;

{
    auto it = std::minmax_element(lhs.begin(), lhs.end());
    lhsMin = *it.first;
    lhsMax = *it.second;
}
Run Code Online (Sandbox Code Playgroud)

或者,你可以使用lambda

int lhsMin, lhsMax;

std::tie(lhsMin, lhsMax) = [&]{
    auto it = std::minmax_element(lhs.begin(), lhs.end());
    return std::make_tuple(*it.first, *it.second);
}();
Run Code Online (Sandbox Code Playgroud)

  • 应该注意的是,它们都不能像OP的第一部分那样用于分配参考.(第二部分被破坏,所以很难说,但它也暗示分配两个`int&s.) (3认同)

Que*_*tin 13

这似乎足以提示辅助函数:

template <class T, std::size_t...Idx>
auto deref_impl(T &&tuple, std::index_sequence<Idx...>) {
    return std::tuple<decltype(*std::get<Idx>(std::forward<T>(tuple)))...>(*std::get<Idx>(std::forward<T>(tuple))...);
}

template <class T>
auto deref(T &&tuple)
    -> decltype(deref_impl(std::forward<T>(tuple), std::make_index_sequence<std::tuple_size<std::remove_reference_t<T>>::value>{})) {
    return deref_impl(std::forward<T>(tuple), std::make_index_sequence<std::tuple_size<std::remove_reference_t<T>>::value>{});
}

// ...

int lhsMin;
int lhsMax;
std::tie(lhsMin,lhsMax) = deref(std::minmax_element(lhs.begin(), lhs.end()));
Run Code Online (Sandbox Code Playgroud)

index_sequence是C++ 14,但可以在C++ 11中实现完整的实现.

注:我会保持在反复decltypederef的返回类型,即使在C++ 14,使SFINAE可以申请.

在Coliru上看到它

  • @ViktorSehr你是什么意思?`std :: tie`返回`std :: tuple <T&>`.但是,所有`std :: tuple`元函数,例如`std :: tuple_size`,也适用于`std :: pair`. (2认同)