我正在尝试使用Dutch national flag algorithm编写quicksort-ish算法。我已经尽了一切努力使这项工作变得非常沮丧。你能看看并帮我找到错误吗?
import random
a = []
for i in range(100):
a.append(random.randint(1, 100))
print(a)
def partion(array, left, right, lPiv, rPiv):
high = len(array) -1
p = left
i = left
while i < high:
if array[i] < lPiv and array[i] < rPiv:
array[i],array[p]=array[p],array[i]
p = p+1
i = i+1
elif array[i] > lPiv and array[i] > rPiv:
array[i],array[high]=array[high],array[i]
high = high-1
else:
i = i+1
return [p, high]
def piv(array, left, right):
aMin = array[left]
aMax = array[left]
for i in array:
if i < aMin:
aMin = i
if i > aMax:
aMax = i
return [aMin + ((aMax - aMin) /3), aMin + ((aMax-aMin)/3)*2]
def sort(array, left, right, depth):
apiv = piv(array, left, right)
part = partion(array, left, right, apiv[0], apiv[1])
if right-left >= 3:
piv1 = piv(array, left, part[0])
part1 = partion(array, left, part[0], piv1[0], piv1[1])
sort(array, left, part1[0], depth+1)
piv2 = piv(array, part[0], part[1])
part2 = partion(array, part[0], part[1], piv2[0], piv2[1])
sort(array, part[0], part[1])
piv3 = piv(array, part[1], right)
part3 = partion(array, part[1], right, piv3[0], piv3[1] )
sort(array, part[1], right)
elif right-left < 3:
if array[right] < array[left]:
array[right],array[left] = array[left], array[right]
else:
return
sort(a, 0, len(a), 1)
print(a)
答案 0 :(得分:1)
您的代码中存在一些错误
if array[right] < array[left]:
和sort(a, 0, len(a), 1)
。
当数组长度为数组时,右数超出数组的索引范围。aMin + ((aMax - aMin) /3)
和aMin + ((aMax-aMin)/3)*2
是相同的索引high = len(array) -1
应该是high = right -1
part1 = partion(array, left, part[0], piv1[0], piv1[1])
错了。 Sort()在它开始时对数组进行分区,不要在同一递归中分区两次。只需调用sort(array,...)。这是我的实施。
import random
from itertools import islice
a = []
for i in range(100):
a.append(random.randint(1, 100))
def partition(array, left, right, lPiv, rPiv):
q = right -1
p = left
r = left
while p<=q:
if array[p]<=lPiv:
array[p], array[r] = array[r], array[p]
p = p+1
r = r+1
elif lPiv<array[p]<=rPiv:
p = p+1
else:
array[p], array[q] = array[q], array[p]
q=q-1
return (p, q+1)
def piv(array, left, right):
aMin = min(islice(a,left,right))
aMax = max(islice(a,left,right))
return (aMin + ((aMax - aMin) /3.0), aMin + ((aMax-aMin)/3.0)*2)
def sort(array, left, right):
if right-left >= 3:
piv_left, piv_right = piv(array, left, right)
if piv_left == piv_right:
return
pt_left, pt_right = partition(array, left, right, piv_left, piv_right)
sort(array, left, pt_left)
sort(array, pt_left, pt_right)
sort(array, pt_right, right)
elif right-left <3:
if left<right and array[right-1] < array[left]:
array[right-1],array[left] = array[left], array[right-1]
sort(a, 0, len(a))
print a
#test
assert( a==sorted(a) )
答案 1 :(得分:0)
pic似乎总是返回相同的值,是吗?也许for循环应该在数组[left:right]上而不是在整个数组上?