问题描述:给定一个数组,给定一个数num,把数组中大于num的数全都放在右边,小于num的都放在左边
分析
1.把数组划分为小于等于num的区域和大于num的区域。用变量x代表小于区域的位置。刚开始由于不存在小于等于的区域,则x = -1,表示指向数组-1(不存在)。再设置变量cur作为遍历的位置,刚开始cur = 0指向数组第一个数。
2.开始遍历
(1)如果cur<=num ,那么把cur当前的元素和小于等于区域的下一个数交换,即++x的位置和cur位置的数交换,cur,x后移;
(2)如果cur>num,cur后移;
(3)如果cur == arr_length结束遍历。
eg [4,6,7,3],num = 5
1.cur 指向4,4<5,把4和x的下一位即0号位置4(自己和自己)交换。之后x指向4,cur++,cur指向6;
2.cur指向6,5<6,x不变,cur++;
3.cur指向7,5<7,x不变,cur++;
4.cur指向3,3<5,交换,x的下一位即6和3交换。之后x指向3,cur++,退出循环。
此时,x指向的3以及之前的4为小于等于区域,而x之后的7,6为大于区域。
(分析转自https://blog.csdn.net/shi_xiao_xuan/article/details/103490390)
#define length 10
int main()
{
int a[length];
int cur = 0;
int x = -1;
int num = 6;
srand((unsigned)time(NULL));
for (int i = 0; i < length; i++)
{
a[i] = rand() % 10;
}
while (cur < length)
{
if (a[cur]<=num)
{
swap(a[cur++], a[++x]);
}
else
{
cur++;
}
}
}
给定一个数组arr,和一个数num,请把小于num的数放在数组的左边,等于num的数放在数组的中间,大于num的数放在数组的右边。要求额外空间复杂度O(1),时间复杂度O(N)
分析
和预备问题相似
1.把数组划分为小于num的区域、等于num的区域和大于num的区域。用变量x代表小于区域的位置、y代表大于num的区域。刚开始由于不存在小于和大于的区域,则x = -1,y = length,表示指向数组-1、length(不存在)。再设置变量cur作为遍历的位置,刚开始cur = 0指向数组第一个数。
2.开始遍历
(1)如果cur<num ,那么把cur当前的元素和小于区域的下一个数交换,即++x的位置和cur位置的数交换,cur,x后移;
(2)如果cur>num,那么把cur当前的元素和大于区域的前一个数交换,即–y的位置和cur位置的数交换,y前移,cur不变(因为交换过来的数不确定)
(3)如果cur == num,cur++。
(4)如果cur == y结束。
while(cur < y)
{
if(arr[cur] < num)
{
swap(arr[cur++],arr[++x]);
}
else if(arr[cur] == num)
{
cur++;
}
else
{
swap(arr[cur],arr[–y]);
}
}