http://www.geeksforgeeks.org/segregate-even-and-odd-numbers/我正在查阅面试问题,并发现了这个有趣的问题。算法看起来很简单,但我想知道是否有可能维持偶数和奇数的顺序,同时仍然保持O(n)的时间复杂度而不使用任何额外的空间。
例如
输入:{12,34,45,9,8,90,3}
输出:{12,34,8,90,45,9,3}
编辑:如果在没有额外空间的情况下无法实现,那么它是否可以使用仅重新排列的整数?因为交换只能在数组中出现
答案 0 :(得分:2)
我认为这是不太可能的,因为没有额外的空间(取决于n
)你必须交换元素,从而使它们混乱(或者你可以在阵列中移动块,但是可能需要非线性的总时间;据我所知,在问题中不允许使用链接列表等其他数据结构。
此问题可以视为稳定的就地非比较排序,其中所有偶数元素都映射到零,并且所有奇数元素都映射到一个用于比较,并且似乎没有符合这些条件的算法(稳定,时间O(n)
,额外记忆O(1)
)(参见例如"非比较排序"表格https://en.wikipedia.org/wiki/Sorting_algorithm#Comparison_of_algorithms)。
答案 1 :(得分:0)
是的,有可能。这个想法是先计算总数,再将奇数一一移到正确的位置。
public void segregateEvenOddWithOrder(int[] arr) {
int countEven = 0;
int length = arr.length;
for (int i = 0; i < length; i++) {
if (arr[i]%2 == 0){
countEven++;
}
}
int i = 0;
int j = i+1;
while (i != countEven){
if (arr[i]%2 == 0){
i++;
j = i + 1;
}else if (arr[i]%2 == 1 && j < length){
int temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
j++;
}
}
}
答案 2 :(得分:0)
这是我的解决方案:
public static void segregateEvenOdd_Sorted_Optimized(int[] arr, int n) {
List<Integer> evenNums = new ArrayList<>();
List<Integer> oddNums = new ArrayList<>();
for (int i = 0; i < n; i++) {
if (arr[i] % 2 == 0) {
evenNums.add(arr[i]);
}
if (arr[i] % 2 == 1) {
oddNums.add(arr[i]);
}
}
Collections.sort(evenNums);
Collections.sort(oddNums);
for (int i = 0; i < evenNums.size() + oddNums.size(); i++) {
if (i < evenNums.size()) {
arr[i] = evenNums.get(i);
} else {
arr[i] = oddNums.get(i - evenNums.size());
}
}
for (int i = 0; i < arr.length; i++) {
System.out.print(arr[i] + " ");
}
}