std::ranges::is_permutation
来自cppreference.com
| 在标头 <algorithm> 定义
|
||
| 调用签名 |
||
| |
(1) | (C++20 起) |
| |
(2) | (C++20 起) |
1) 若存在范围
[first1, last1) 中的元素的排列使得该范围等于 [first2, last2)(在应用对应的投影 Proj1 和 Proj2 后,并以 Pred 为比较器)则返回 true。否则返回 false。2) 同 (1),但以
r1 为第一源范围并以 r2 为第二源范围,如同以 ranges::begin(r1) 为 first1,以 ranges::end(r1) 为 last1,以 ranges::begin(r2) 为 first2,并以 ranges::end(r2) 为 last2。此页面上描述的函数式实体是算法函数对象(非正式地称为 niebloid),即:
参数
| first1, last1 | - | 第一元素范围的迭代器-哨位对 |
| first2, last2 | - | 第二元素范围的迭代器-哨位对 |
| r1 | - | 第一元素 range
|
| r2 | - | 第二元素 range
|
| pred | - | 应用到投影后元素的谓词 |
| proj1 | - | 应用到第一范围中元素的投影 |
| proj2 | - | 应用到第一范围中元素的投影 |
返回值
若范围 [first1, last1) 为 [first2, last2) 的重排列则为 true。
复杂度
至多应用 O(N2) 次谓词和每个投影,或若序列已经相等则恰好应用 N 次,其中 N 为 ranges::distance(first1, last1)。
然而若 ranges::distance(first1, last1) != ranges::distance(first2, last2),则不应用谓词和投影。
注解
排列 关系是等价关系。
ranges::is_permutation 可以用于测试,比如检查诸如排序、混洗、划分等重排算法的正确性。若 p 为原序列而 q 是“改动后”的序列,则 ranges::is_permutation(p, q) == true 表示构成 q 的元素与 p 的“相同”(可能经过重排)。
可能的实现
|
示例
运行此代码
#include <algorithm>
#include <array>
#include <cmath>
#include <iostream>
#include <ranges>
auto& operator<<(auto& os, std::ranges::forward_range auto const& v)
{
os << "{ ";
for (const auto& e : v)
os << e << ' ';
return os << "}";
}
int main()
{
static constexpr auto r1 = {1, 2, 3, 4, 5};
static constexpr auto r2 = {3, 5, 4, 1, 2};
static constexpr auto r3 = {3, 5, 4, 1, 1};
static_assert(
std::ranges::is_permutation(r1, r1) &&
std::ranges::is_permutation(r1, r2) &&
std::ranges::is_permutation(r2, r1) &&
std::ranges::is_permutation(r1.begin(), r1.end(), r2.begin(), r2.end()));
std::cout
<< std::boolalpha
<< "is_permutation(" << r1 << ", " << r2 << "): "
<< std::ranges::is_permutation(r1, r2) << '\n'
<< "is_permutation(" << r1 << ", " << r3 << "): "
<< std::ranges::is_permutation(r1, r3) << '\n'
<< "is_permutation with custom predicate and projections: "
<< std::ranges::is_permutation(
std::array{ -14, -11, -13, -15, -12 }, // 第一范围
std::array{ 'F', 'E', 'C', 'B', 'D' }, // 第二范围
[](int x, int y) { return abs(x) == abs(y); }, // 谓词
[](int x) { return x + 10; }, // 第一范围的投影
[](char y) { return int(y - 'A'); }) // 第二范围的投影
<< '\n';
}
输出:
is_permutation({ 1 2 3 4 5 }, { 3 5 4 1 2 }): true
is_permutation({ 1 2 3 4 5 }, { 3 5 4 1 1 }): false
is_permutation with custom predicate and projections: true
参阅
(C++20) |
生成元素范围的下一个字典序更大的排列 (算法函数对象) |
(C++20) |
生成元素范围的下一个字典序更小的排列 (算法函数对象) |
(C++11) |
判断一个序列是否为另一个序列的排列 (函数模板) |
| 生成元素范围的下一个字典序更大的排列 (函数模板) | |
| 生成元素范围的下一个字典序更小的排列 (函数模板) | |
(C++20) |
指定 relation 施加等价关系 (概念) |