Title: Sorting The Short Version
1Sorting (The Short Version)
- Reading 10.1 (but be careful about the
"generics") 10.2 10.7 - The Problem
- Take a collection (actually a List) that has
Comparable elements in it - Re-arrange the elements in the List so that if X
and Y are any two items in the list, and
theList.indexOf(X) lt theList.indexOf(Y), then
X.compareTo(Y) lt 0 - In other words, put the items in the list in
order according to the "natural order" of the
elements - There are many minor variants
- instead of sorting "in place" return a sorted
copy - instead of sorting in ascending order, sort in
descending order
2Java's Built-In Sort Methods
class Employee implements Comparable
protected int id protected String name
protected double salary public Employee(int
id, String name, double salary) this.id
id this.name name this.salary
salary public int compareTo(Object o)
Employee eo (Employee) e if (id lt eo.id)
return -1 if (id eo.id) return 0
return 1
ArrayList al new ArrayList() al.add(new
Employee(1, "Joe", 12.5)) al.add(new Employee(2,
"Adam", 10.0)) al.add(new Employee(3, "Sally",
25.0)) Collections.sort(al) // List is now in
order according to ID
3When the Natural Order Isn't The Right Order
- Suppose you want to sort by name
- a reasonable thing to do
- extremely difficult given what we know so far,
since it involves changing the class's compareTo
method - the solution provide a different comparator
method for the purposes of sorting
Comparator cn new NameComparator() Collections.
sort(al, cn) class NameComparator implements
Comparator public int compare(Object e1,
Object e2) return ((Employee)e1).name.compar
eTo(((Employee) e2).name)
4Sorting it Yourself
- These algorithms don't depend on a particular
collection implementation (array, ArrayList,
LinkedList), only that you have - positional access arrayi or arrayList.get(i)
- access to the collection's length array.length
or arrayList.size() - the ability to swap two elements in the
collection ai value or arrayList.set(i,
value) - the ability to compare two elements in the
collection -- lt or compareTo
5Selection Sort
- We maintain just one pointer (index) the index
of part of the array known to be sorted - We begin with sorted -1 when sorted length
1, we know that the list is entirely sorted
every iteration through the loop we - swap the smallest element in the range sorted-1,
length-1 with the element at sorted-1, and
increment sorted
-2
0
4
1
0
12
sorted 1 (all elements 1 and "to the left" are
known to be sorted after that we don't know)
6Selection Sort (cont.)
initially
sorted
after 1 iteration
sorted
after 2 iterations
sorted
after 5 iterations (done)
sorted
7Selection Sort Algorithm Shell
public static void selectionSort(List l)
for (int sorted -1 sorted lt l.size() - 1
sorted) int swapper
findIndexOfSmallest(l, sorted1) swap(l,
sorted1, swapper)
public static void selectionSort(int array)
for (int sorted -1 sorted lt array.length -
1 sorted) int swapper
findIndexOfSmallest(array, sorted1)
swap(array, sorted1, swapper)
-- Array and List versions are essentially
identical -- findIndexOfSmallest is a 142 problem
(think about how you would do it if all
you knew about the elements of the array were
that they implemented Comparable)
8Advantages and Disadvantages of Selection Sort
- Easy to understand and implement
- Slow in that size of the "solved problem"
decreases by 1 every time through the loop - Slow in that elements near the end of the array
are examined over and over again unnecessarily? - Remember the jump from finding an element in a
list using linear search versus binary search - in linear search, the "unsearched" part of the
list decreased by 1 - in binary search, the "unsearched" part of the
list decreased by ½ - The question can we devise the same kind of
scheme where we reduce the size of the sort by ½
every time through the loop - the answer sort of
9Merge Sort The Intuition
0
-2
4
1
0
12
initially
after first split two shorter unsorted lists
0
-2
4
1
0
12
0
1
after last split lists of length 1 are easy to
sort!
-2
4
0
12
10Merge Sort Combining the Sorted Lists
-2
0
0
1
4
12
-2
0
4
0
1
12
0
1
11The Merge Function
- Input two lists L1 and L2 in sorted order
- Output a list L3 with the elements of L1 and L2
in sorted order - The basic idea
- pre-allocate an empty output list
- maintain pointers to the two input lists,
indicating the next element to be copied. Choose
the smaller, copy it, and update the appropriate
pointers
-2
0
4
0
1
next
next
next
12Merging (cont.)
-2
0
4
0
1
-2
0
4
0
1
-2
-2
0
4
0
1
-2
0
-2
0
4
0
1
-2
0
0
-2
0
4
0
1
-2
0
0
1
-2
0
4
0
1
-2
0
0
1
4
13Merging The Code
public static List merge(List l1, List l2)
ArrayList out new ArrayList() int next1 0
// Next available item in l1 int next2 0
// Next available item in l2 while (next1
lt l1.size() next2 lt l2.size()) if
(next1 gt l1.size()) // L1 is empty but L2
is not out.add(l2.get(next2))
next2 else if (next2 gt l2.size())
// L2 is empty but L1 is not
out.add(l1.get(next1)) next1
else // Neither input list is empty
Comparable c1 (Comparable)l1.get(next1)
Comparable c2 (Comparable)l2.get(next2)
if (c1.compareTo(c2) lt 0)
out.add(c1) next1 else
out.add(c2) next2
// Both input lists are empty
return out
14MergeSort The Payoff
public static List mergeSort(List theList) if
(theList.size() lt 1) return theList
else List fh theList.subList(0,
theList.size()/2) List sh
theList.subList(theList.size()/2,
theList.size()) return merge(mergeSort(fh),
mergeSort(sh))