简体   繁体   中英

How to sort even and odd numbers alternatively with the limit of time and space complexity?(C/C++)

Given a integer array like

int numbers[8]={1, 3, 5, 7, 8, 6, 4, 2};

The half side in the front array are odd numbers, and the rest (the equal amount number) are even. The odd numbers are in an ascending order and even part are in a descending order. After the sorting, the order of the numbers can't be changed.

How can I sort them alternatively with time complexity less than O(n^2) and space complexity O(1) ?

For this example, the result would be: {1,8,3,6,5,4,7,2} ;

I can't use external array storage but temporary variables are acceptable.

I have tried to use two pointers( oddPtr, evenPtr ) to point odd and even numbers separately, and move evenPtr to insert the even values to the middles of odd numbers.(Like insertion sort)
But it takes O(n^2) .

UPDATED

As per Dukeling's comment I realized that the solution I propose in fact is not linear,but linearithmic and even worse - you can't control if it takes extra memory or not. On my second thought I realized you know a lot about the array you to implement a more specific, but probably easier solution.

I will make an assumption that all values in the array are positive. I need this so that I can use negative values as kind of 'already processed' flag. My idea is the following - iterate over the array from left to right. For each element if it is already processed(ie its value is negative) simply continue with the next one. Otherwise you will have a constant formula where is the position where this element should be:

  • If the value is odd and its index is i it should move to i*2
  • If the value is even and its index is i it should move to (i - n/2)*2 + 1

Store this value into a temporary and make the value at the current index of the array 0. Now until the position where the value we 'have at hand' is not zero, swap it with the value staying at the position we should place it according to the formula above. Also when you place the value at hand negate it to 'mark it as processed'. Now we have a new value 'at hand' and again we calculate where it should go according to the formula above. We continue moving values until the value we 'have at hand' should go to the position with 0. With a little thought you can prove that you will never have a negative('processed') value at hand and that eventually you will end up at the empty spot of the array.

After you process all the values iterate once over the array to negate all values and you will have the array you need. The complexity of the algorithm I describe is linear- each value will be no more than once 'at hand' and you will iterate over it no more than once.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM