一、题目:
将序列前半部分为负整数,后半部分为正整数,不要求排序,但要求尽量减少交换次数。
二、思路:
首先,从数组0开始往后找第一个正整数位置pos;然后,从数组len-1开始往前找第一个负整数位置neg;
接着,交换这两个数。pos往后找,neg往前找。重复前面步骤,直到pos>=neg结束。
三、实现程序
#include <iostream>
// 交换两个数
void Swap(int &a, int &b) {
int temp;
temp = a;
a = b;
b = temp;
}
// 将负整数放在左边,正整数放在右边
int divPosNeg(int arr[], int len) {
int neg = len-1, pos = 0; // neg,pos分别存储找到的负整数和正整数的位置
int i, count = 0; // count记录交换次数
while(pos < neg) {
for(i = pos; i < len; i++) // // 往右扫描,找到第一个正整数
if(arr[i] > 0) {
pos = i;
break;
}
// 从右边开始找第一个负数
for(int i = neg; i >= 0; i--)
if(arr[i] < 0) {
neg = i;
break;
}
Swap(arr[pos], arr[neg]); // 交换
count++;
pos++;
neg--;
}
return count;
}
int main(int argc, const char * argv[]) {
// insert code here...
int arr[] = {10, 10, -20, 30, 40, -50, 60, -70, 80, -90, -100};
int len, i, count;
len = sizeof(arr) / sizeof(arr[0]); // 获取整个数组的长度
// 输出分类前
for(i = 0; i < len; i++)
std::cout << arr[i] << " ";
std::cout << std::endl;
count = divPosNeg(arr, len); // 调用数据分类函数
for(i = 0; i < len; i++)
std::cout << arr[i] << " ";
std::cout << std::endl;
std::cout << "交换的次数:" << count << std::endl;
return 0;
}
运行结果: