正负数排序问题
题目:
- 输入一个数组,要求将负数排在正数前面
- 输入:[ 1,-2,-3,0,7,-6 ]
- 输出:[-6, -2, -3, 0, 7, 1]
分析:
- 设置头指针top,从头往后找正数
- 设置尾指针end,从后往头找负数
/**
* 交换算法:设置头指针top,尾指针end
* top++,end--
* 若 arr[top] > 0 && arr[end] < 0,则交换
*/
public static void swap(int[] array){
int top = 0;
int end = array.length - 1;
int tmpt;
while (top < end){
//top找到大于0
while (array[top] < 0 && top < end){
top++;
}
//end找到小于0
while (array[end] > 0 && top < end){
end--;
}
//交换
tmpt = array[top];
array[top] = array[end];
array[end] = tmpt;
//若交换的值为0,则跳过,防止输入中含有重复的 0 而出现无限循环
if (array[top] == 0){
top++;
}
if (array[end] == 0){
end--;
}
}
System.out.println(Arrays.toString(array));
}
还未解决两个0问题
- 时间复杂度:O(n*logn)
三色排序练问题
有一个只由0
,1
,2
三种元素构成的整数数组,请使用交换、原地排序而不是使用计数进行排序。给定一个只含0,1,2的整数数组A及它的大小,请返回排序后
的数组。保证数组大小小于等于500。
测试样例:[0,1,1,0,2,2],6
返回: [0,0,1,1,2,2]
解析:运用快排
的原理。用数字1
来处理,在数组左右各维护一个小于区间和大于区间。
public int[] mergeSort(int[] a, int n)
{
return doMergeSort(a, n, 0, n - 1);
}
public int[] doMergeSort(int[] a, int n, int start, int end)
{
int[] res = new int[n];
if (n <= 1)
{
res[0] = a[start];
return res;
}
// n>=2时,对其左右数组进行处理
int half = n / 2;
int leftEnd = start + half - 1;
int rightStart = leftEnd + 1;
//递归调用本函数,获取有序的左数组以及右数组
int[] left = doMergeSort(a, half, start, leftEnd);
int[] right = doMergeSort(a, n - half, rightStart, end);
// 将左右序列合并
int k = 0, i = 0, j = 0;
while (i < half && j < n - half)
{//由前往后比较两个序列,取较小值填充到res中,取值后该序列往后移动取下一个值比较
if (left[i] <= right[j])
{
res[k++] = left[i++];
}
else
{
res[k++] = right[j++];
}
}
// 剩余的直接放入
while (i < half)
{
res[k++] = left[i++];
}
while (j < n - half)
{
res[k++] = right[j++];
}
return res;
}