forked from kamyu104/LeetCode-Solutions
-
Notifications
You must be signed in to change notification settings - Fork 0
/
sort-even-and-odd-indices-independently.py
82 lines (74 loc) · 2.89 KB
/
sort-even-and-odd-indices-independently.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
# Time: O(n)
# Space: O(c), c is the max of nums
# counting sort, inplace solution
class Solution(object):
def sortEvenOdd(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
def partition(index, nums):
for i in xrange(len(nums)):
j = i
while nums[i] >= 0:
j = index(j)
nums[i], nums[j] = nums[j], ~nums[i] # processed
for i in xrange(len(nums)):
nums[i] = ~nums[i] # restore values
def inplace_counting_sort(nums, left, right, reverse=False): # Time: O(n)
if right-left+1 == 0:
return
count = [0]*(max(nums[i] for i in xrange(left, right+1))+1)
for i in xrange(left, right+1):
count[nums[i]] += 1
for i in xrange(1, len(count)):
count[i] += count[i-1]
for i in reversed(xrange(left, right+1)): # inplace but unstable sort
while nums[i] >= 0:
count[nums[i]] -= 1
j = left+count[nums[i]]
nums[i], nums[j] = nums[j], ~nums[i]
for i in xrange(left, right+1):
nums[i] = ~nums[i] # restore values
if reverse: # unstable
while left < right:
nums[left], nums[right] = nums[right], nums[left]
left += 1
right -= 1
partition(lambda i: i//2 if i%2 == 0 else (len(nums)+1)//2+i//2, nums)
inplace_counting_sort(nums, 0, (len(nums)+1)//2-1)
inplace_counting_sort(nums, (len(nums)+1)//2, len(nums)-1, True)
partition(lambda i: 2*i if i < (len(nums)+1)//2 else 1+2*(i-(len(nums)+1)//2), nums)
return nums
# Time: O(nlogn)
# Space: O(n)
# sort, inplace solution
class Solution2(object):
def sortEvenOdd(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
def partition(index, nums):
for i in xrange(len(nums)):
j = i
while nums[i] >= 0:
j = index(j)
nums[i], nums[j] = nums[j], ~nums[i] # processed
for i in xrange(len(nums)):
nums[i] = ~nums[i] # restore values
partition(lambda i: i//2 if i%2 == 0 else (len(nums)+1)//2+i//2, nums)
nums[:(len(nums)+1)//2], nums[(len(nums)+1)//2:] = sorted(nums[:(len(nums)+1)//2]), sorted(nums[(len(nums)+1)//2:], reverse=True)
partition(lambda i: 2*i if i < (len(nums)+1)//2 else 1+2*(i-(len(nums)+1)//2), nums)
return nums
# Time: O(nlogn)
# Space: O(n)
# sort
class Solution3(object):
def sortEvenOdd(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
nums[::2], nums[1::2] = sorted(nums[::2]), sorted(nums[1::2], reverse=True)
return nums