Question: I'm 2 hours into my reading of *diveintopython* and I implemented a naive version of quicksort. 

```
import operator

def even(num):
    return operator.mod(num,2) == 0

def last(list):
    return len(list)-1

def median(list):
    if even(len(list)):
        return len(list)/2 - 1
    else:
        return len(list)/2

def sort(list, pivot_selector):
    if len(list) <= 1:
        return list
    else:
        i = pivot_selector(list)
        pivot = list[i]
        less, greater, equal = [], [], []
        for x in list:
            if x < pivot:
                less.append( x )
            elif x == pivot:
                equal.append( x )
            else:
                greater.append( x )

    return sort(less, pivot_selector) + equal + sort(greater, pivot_selector)

if __name__ == "__main__":
    print sort([5,4,3,2],median)
    print sort([],median)
    print sort([2],median)
    print sort([3,2],median)
    print sort([3,2,3],median)
    print sort([1,3,2],median)
    print sort([1,'a',0],median)
    print sort([None,1,0],median)

```

5 questions:

1. This code resides in a file called quicksort.py. How does one hide the method *even* from being exported to the public.
2. Is it pythonic to pass in a \*pivot\_selector\* as a parameter ?
3. Anything wrong or suboptimal with my quicksort implementation ?
4. How would you allow the user to specify a comparator that will enforce a custom ordering on the list elements ?
5. Is there a pythonic way to enforce a constraint that the list parameter must contain homogeneous types ?

Answer: 
> 
> 1 - This code resides in a file called quicksort.py. How does one hide the method even from being exported to the public.
> 
> 
> 

The convention is to name functions private to your module [with an underscore at the beginning](http://docs.python.org/tutorial/modules.html#more-on-modules).

> 
> 2 - Is it pythonic to pass in a \*pivot\_selector\* as a parameter ?
> 
> 
> 

Since Python has first class functions it's fine to pass functions around as parameters.

> 
> 3 - Anything wrong or suboptimal with my quicksort implementation ?
> 
> 
> 

The use of an `equal` list seems non-traditional to me. [Usually items equal to the pivot end up in the `greater` list.](http://en.wikipedia.org/wiki/Quicksort)

> 
> 4 - How would you allow the user to specify a comparator that will enforce a custom ordering on the list elements ?
> 
> 
> 

The standard Python `sort()` and [`sorted()`](http://docs.python.org/library/functions.html#sorted) functions have an optional parameter for a comparison function. This seems the best way to do it.

> 
> 5 - Is there a pythonic way to enforce a constraint that the list parameter must contain homogeneous types ?
> 
> 
> 

In Python you normally don't worry about this. Python has the [concept of duck-typing](http://docs.python.org/glossary.html#term-duck-typing), so if an object does what it's supposed to we don't worry about checking its type beforehand. This is often expressed as "It's easier to ask for forgiveness than permission."

So let the user of your module worry about the Exception that will be thrown if they pass in a list of objects to sort which can't be compared to each other.
The only thing I'd like to add is that creating three lists and growing them one element at a time looks rather sub-optimal. A typical quicksort implementation (in Python or not) moves elements around in the existing list.