Advertisement
asweigart

quickselect

Apr 4th, 2019
275
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 1.61 KB | None | 0 0
  1. import random
  2.  
  3. import logging
  4. logging.basicConfig(level=logging.DEBUG, format='%(levelname)s - %(message)s')
  5. logging.disable(logging.CRITICAL)
  6.  
  7. def quickselect(items, kth, left=0, right=None):
  8. if (len(items) == 0) or (not (0 <= kth < len(items))):
  9. return None
  10.  
  11. if right is None:
  12. right = len(items) - 1 # `right` defaults to the last index in items.
  13.  
  14. if left == right:
  15. return items[left] # BASE CASE
  16.  
  17. logging.debug(f'pivot/leftval={items[left]}, rightval={items[right]} items={items}')
  18.  
  19. # Partition step:
  20. i = left
  21. for j in range(left + 1, right + 1):
  22. logging.debug(f'i={i}, j={j}, left={left}, comparing {items[j]} < {items[left]}')
  23. if items[j] < items[left]:
  24. i += 1
  25. items[i], items[j] = items[j], items[i]
  26. logging.debug(f'i={i}, j={j}, swapped i and j: {items[i]} and {items[j]}, items={items}')
  27.  
  28. # Move the pivot to the correct location:
  29. items[i], items[left] = items[left], items[i]
  30.  
  31. # Recursively partition one side only:
  32. if kth == i: # We've sorted kth items in `items`.
  33. return items[i] # BASE CASE
  34. elif i < kth: # TODO We haven't "sorted" enough of `items`, sort items to the right of the pivot.
  35. return quickselect(items, kth, i + 1, right) # RECURSIVE CASE
  36. else: # We've "sorted" too many
  37. return quickselect(items, kth, left, i - 1) # RECURSIVE CASE
  38.  
  39.  
  40. #a = [6, 0, 2, 16, 14, 10, 18, 20, 12, 4, 8] # kth == i case
  41. a = [18, 20, 14, 16, 4, 10, 6, 2, 8, 0, 12]
  42. print(a)
  43. logging.debug(f'Searching for kth of 3 in {a}')
  44. print(quickselect(a, 3))
  45. print(a)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement