Lecture 06 Ticket Solution

Complete before the beginning of class on Wednesday, 09/14.

Download this ticket in pdf format or .tex source.

\[\def\compare{ {\mathrm{compare}} } \def\swap{ {\mathrm{swap}} } \def\sort{ {\mathrm{sort}} } \def\true{ {\mathrm{true}} } \def\false{ {\mathrm{false}} } \def\split{ {\mathrm{split}} } \def\val{ {\mathrm{val}} } \def\lft{ {\mathrm{left}} } \def\rt{ {\mathrm{right}} } \def\size{ {\mathrm{size}} }\]

Suppose \(a\) is an array of numerical values of size \(n\), and \(\val\) is a numerical value. Write a method \(\split(a, \val)\) with the following behavior:

  1. \(\split\) only modifies \(a\) using the operation \(\swap(a, i, j)\) that swaps the values of \(a\) at indices \(i\) and \(j\),
  2. after calling \(\split(a, \val)\), there is an index \(k\) with \(1 \leq k \leq n\) such that for all indices \(i < k\), \(a[i] \leq \val\) and for all \(j \geq k\), \(a[j] > \val\), and
  3. \(\split\) returns the index \(k\) as in item 2.

Solution

Here is one (of many possible) ways of accomplishing this:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
Split(a, val):
  left <- 1         # left index
  right <- size(a)  # right index
  while left < right do
    if a[left] > val and a[right] <= val then
	  swap(a, left, right)
	  left <- left + 1
	  right <- right - 1
	else
	  if a[left] <= val then 
	    left <- left + 1
	  endif
	  if a[right] > val then
	    right <- right - 1
	  endif
	endif
  endwhile
  return right + 1

To understand why this method works, we make the following observations:

  1. After each iteration of the loop, we have \(a[i] \leq \val\) for all indices \(i < \lft\) and \(a[j] > \val\) for all indices \(j > \rt\).

  2. In each iteration of the loop, \(\lft\) gets increment or \(\rt\) gets decremented (or both).

The second observation implies that the loop terminates after at most \(\size(a)\) iterations. The first observation shows that when the loop terminates, the split is correctly performed.