什么是荷兰国旗问题
荷兰国旗是由红白蓝3种颜色的条纹拼接而成,如下图所示:
假设这样的条纹有多条,且各种颜色的数量不一,并且随机组成了一个新的图形,新的图形可能如下图所示,但是绝非只有这一种情况:
需求是:把这些条纹按照颜色排好,红色的在上半部分,白色的在中间部分,蓝色的在下半部分,我们把这类问题称作荷兰国旗问题。
我们把荷兰国旗问题用数组的形式表达一下是这样的:
给定一个整数数组,给定一个值K,这个值在原数组中一定存在,要求把数组中小于K的元素放到数组的左边,大于K的元素放到数组的右边,等于K的元素放到数组的中间,最终返回一个整数数组,其中只有两个值,分别是等于K的数组部分的左右两个下标值。
例如,给定数组:[2, 3, 1, 9, 7, 6, 1, 4, 5],给定一个值4,那么经过处理原数组可能得一种情况是:[2, 3, 1, 1, 4, 9, 7, 6, 5],需要注意的是,小于4的部分不需要有序,大于4的部分也不需要有序,返回等于4部分的左右两个下标,即[4, 4]
实现
思路
我们以上面举的例子来看看处理过程的图示:
- less 用于记录小于 4 的区域的右下标,初始为-1,表示不存在小于4的
- more 用于记录大于 4 区域的左下标,初始为9,表示不存在大于4的
- L 用于正在遍历的元素的下标,初始值为0
从 arr[L] 即 arr[0] 开始遍历数组
std::vector<int> partition(std::vector<int> &arr, int L, int R, int priv){
int less = L - 1;
int more = R + 1;
int curr = L; // 就是上图的L,当然也可以写成下面那样
while (curr < more){
if(arr[curr] < priv){
std::swap(arr[curr++], arr[++less]);
}else if(arr[curr] > priv){
std::swap(arr[curr] , arr[--more]);
}else{
curr++;
}
}
return { less + 1, more - 1 }; // 和p相等的边界
}
std::vector<int> partition(std::vector<int> &arr, int L, int R, int priv){
int less = L - 1;
int more = R + 1;
while (L < more){
if(arr[L] < priv){
std::swap(arr[L++], arr[++less]);
}else if(arr[L] > priv){
std::swap(arr[L] , arr[--more]);
}else{
L++;
}
}
return { less + 1, more - 1 }; // 和p相等的边界
}
原文地址:https://www.jb51.cc/wenti/3282990.html
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。