# 24 Algorithms library [algorithms]

## 24.7 Sorting and related operations [alg.sorting]

### 24.7.11 Three-way comparison algorithms [alg.3way]

```template<class T, class U> constexpr auto compare_3way(const T& a, const U& b); ```
Effects: Compares two values and produces a result of the strongest applicable comparison category type:
• Returns a <=> b if that expression is well-formed.
• Otherwise, if the expressions a == b and a < b are each well-formed and convertible to bool, returns strong_­ordering::equal when a == b is true, otherwise returns strong_­ordering::less when a < b is true, and otherwise returns strong_­ordering::greater.
• Otherwise, if the expression a == b is well-formed and convertible to bool, returns strong_­equality::equal when a == b is true, and otherwise returns strong_­equality::nonequal.
• Otherwise, the function is defined as deleted.
```template<class InputIterator1, class InputIterator2, class Cmp> constexpr auto lexicographical_compare_3way(InputIterator1 b1, InputIterator1 e1, InputIterator2 b2, InputIterator2 e2, Cmp comp) -> common_comparison_category_t<decltype(comp(*b1, *b2)), strong_ordering>; ```
Requires: Cmp shall be a function object type whose return type is a comparison category type.
Effects: Lexicographically compares two ranges and produces a result of the strongest applicable comparison category type.
Equivalent to:
```for ( ; b1 != e1 && b2 != e2; void(++b1), void(++b2) )
if (auto cmp = comp(*b1,*b2); cmp != 0)
return cmp;
return b1 != e1 ? strong_ordering::greater :
b2 != e2 ? strong_ordering::less :
strong_ordering::equal;
```
```template<class InputIterator1, class InputIterator2> constexpr auto lexicographical_compare_3way(InputIterator1 b1, InputIterator1 e1, InputIterator2 b2, InputIterator2 e2); ```
Effects: Equivalent to:
```return lexicographical_compare_3way(b1, e1, b2, e2,
[](const auto& t, const auto& u) {
return compare_3way(t, u);
});
```