Survey
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Chapter 14 Programming Exercise Solutions P14.1 /** The sort method of this class sorts an array, using the selection sort algorithm. */ public class SelectionSorter { /** Sorts an array, using selection sort. @param a the array to sort */ public static void sort(int[] a) { for (int i = 0; i < a.length - 1; i++) { int maxPos = maximumPosition(a, i); ArrayUtil.swap(a, maxPos, i); } } /** Finds the largest element in a tail range of the array. @param a the array to sort @param from the first position in a to compare @return the position of the largest element in the range a[from] . . . a[a.length - 1] */ private static int maximumPosition(int[] a, int from) { int maxPos = from; for (int i = from + 1; i < a.length; i++) { if (a[i] > a[maxPos]) { maxPos = i; } } return maxPos; } } P14.2 /** The sort method of this class sorts an array of coins, using the selection sort algorithm. */ public class SelectionSorter { /** Sorts an array of coin objects, using selection sort. @param a the array to sort */ © John Wiley & Sons, Inc. All rights reserved. 1 public static void sort(Coin[] a) { for (int i = 0; i < a.length - 1; i++) { int minPos = minimumPosition(a, i); ArrayUtil.swap(a, minPos, i); } } /** Finds the smallest coin in a tail range of the array. @param a the array to sort @param from the first position in a to compare @return the position of the smallest coin in the range a[from] . . . a[a.length - 1] */ private static int minimumPosition(int[] a, int from) { int minPos = from; for (int i = from + 1; i < a.length; i++) { if (a[i].getValue() < a[minPos].getValue()) { minPos = i; } } return minPos; } /** Swaps two entries of an array of Coin objects. @param a the array @param i the first position to swap @param j the second position to swap */ public static void swap(Coin[] a, int i, int j) { Coin temp = a[i]; a[i] = a[j]; a[j] = temp; } } P14.3 import java.util.Scanner; /** This class tests the SelectionSorter class. */ public class SelectionSorterTimer { public static void main(String[] args) { Scanner in = new Scanner(System.in); System.out.println("Enter smallest array size:"); int n1 = in.nextInt(); © John Wiley & Sons, Inc. All rights reserved. 2 System.out.println("Enter largest array size:"); int n2 = in.nextInt(); System.out.println("Enter number of measurements (>=2):"); int m = in.nextInt(); for (int i = 0; i < m; i++) { int n = n1 + i * (n2 - n1) / (m - 1); int[] a = ArrayUtil.randomIntArray(n, 100); // use stopwatch to time selection sort StopWatch timer = new StopWatch(); timer.start(); SelectionSorter s = new SelectionSorter(a); s.sort(); timer.stop(); System.out.println("n:" + n + ". Elapsed time: " + timer.getElapsedTime() + " milliseconds"); } } } P14.4 /** This class sorts an array of strings in lexicographical order, using the merge sort algorithm. */ public class MergeSorter { /** Sorts an array of Strings using merge sort. @param a an array of Strings */ public static void sort(String[] a) { if (a.length <= 1) { return; } String[] first = new String[a.length / 2]; String[] second = new String[a.length - first.length]; // Copy the first half of a into first, the second half into second for (int i = 0; i < first.length; i++) { first[i] = a[i]; } for (int i = 0; i < second.length; i++) { second[i] = a[first.length + i]; } sort(first); sort(second); merge(first, second, a); } /** Merges two sorted arrays into an array. © John Wiley & Sons, Inc. All rights reserved. 3 @param first the first sorted array @param second the second sorted array @param a the array of Strings */ private static void merge(String[] first, String[] second, String[] a) { int iFirst = 0; // Next element to consider in the first array int iSecond = 0; // Next element to consider in the second array int j = 0; // Next open position in a // As long as neither iFirst nor iSecond is past the end, move // the smaller element into a while (iFirst < first.length && iSecond < second.length) { if (first[iFirst].compareTO(second[iSecond]) < 0) { a[j] = first[iFirst]; iFirst++; } else { a[j] = second[iSecond]; iSecond++; } j++; } // Note that only one of the two loops below copies entries // Copy any remaining entries of the first array while (iFirst < first.length) { a[j] = first[iFirst]; iFirst++; j++; } // Copy any remaining entries of the second half while (iSecond < second.length) { a[j] = second[iSecond]; iSecond++; j++; } } } P14.5 /** An item with a */ public class Item { private String private String key and a value. implements Comparable<Item> key; value; /** Constructs an Item object. © John Wiley & Sons, Inc. All rights reserved. 4 @param k the key string @param v the value of the item */ public Item(String k, String v) { key = k; value = v; } /** Gets the key. @return the key */ public String getKey() { return key; } /** Gets the value. @return the value */ public String getValue() { return value; } public int compareTO(Item otherObject) { Item other = (Item) otherObject; return key.compareTO(other.key); } } -------------------------------------------import java.util.ArrayList; import java.util.Collections; import java.util.Scanner; /** A table for lookups and reverse lookups */ public class LookupTable { private ArrayList<Item> byKey; private ArrayList<Item> byValue; /** Constructs a LookupTable object. */ public LookupTable() { byKey = new ArrayList<Item>(); byValue = new ArrayList<Item>(); } © John Wiley & Sons, Inc. All rights reserved. 5 /** Reads key/value pairs. @param in the scanner for reading the input */ public void read(Scanner in) { while (in.hasNextLine()) { String k = in.nextLine(); String v = in.nextLine(); byKey.add(new Item(k, v)); byValue.add(new Item(v, k)); } Collections.sort(byKey); Collections.sort(byValue); } /** Looks up an item in the table. @param k the key to find @return the value with the given key, or null if no such item was found. */ public String lookup(String k) { int pos = Collections.binarySearch(byKey, new Item(k, null)); if (pos < 0) { return null; } else { return byKey.get(pos).getValue(); } } /** Looks up an item in the table. @param v the value to find @return the key with the given value, or null if no such item was found. */ public String reverseLookup(String v) { int pos = Collections.binarySearch(byValue, new Item(v, null)); if (pos < 0) { return null; } else { return byValue.get(pos).getValue(); } } } © John Wiley & Sons, Inc. All rights reserved. 6 P14.6 Uses special_topic_2/InsertionSorter.java, section_2/Stopwatch.java, and ArrayUtil.java from your companion code. /** This program measures how long it takes to sort an array of a user-specified size with the insertion sort algorithm. */ public class InsertionSortTimer { public static void main(String[] args) { Scanner in = new Scanner(System.in); System.out.print("Enter array size: "); int n = in.nextInt(); // Construct random array int[] a = ArrayUtil.randomIntArray(n, 100); // Use stopwatch to time insertion sort StopWatch timer = new StopWatch(); timer.start(); InsertionSorter.sort(a); timer.stop(); System.out.println("Elapsed time: " + timer.getElapsedTime() + " milliseconds"); } } P14.7 Uses section_2/ArrayUtil.java from your companion code. public class BubbleSorter { public static void sort(int[] arr) { boolean swapped = true; int j = 0; int tmp; while (swapped) { swapped = false; j++; for (int i = 0; i < arr.length - j; i++) { © John Wiley & Sons, Inc. All rights reserved. 7 if (arr[i] > arr[i + 1]) { tmp = arr[i]; arr[i] = arr[i + 1]; arr[i + 1] = tmp; swapped = true; } } } } } --------------------------------------------------import java.util.Arrays; /** This program demonstrates the bubble sort algorithm by sorting an array that is filled with random numbers. */ public class BubbleSortDemo { public static void main(String[] args) { int[] a = ArrayUtil.randomIntArray(20, 100); System.out.println(Arrays.toString(a)); BubbleSorter.sort(a); System.out.println(Arrays.toString(a)); } } P14.8 Uses section_2/ArrayUtil.java from your companion code. public class FrequentFinder { /** Count the occurrences of a value in an array. @param a the array @param value the value to count @return the number of occurrences of a */ public static int count(int[] a, int value) { int count = 0; for (int i = 0; i < a.length; i++) { if (a[i] == value) { count++; } } return count; } © John Wiley & Sons, Inc. All rights reserved. 8 /** Find the value that occurs most frequently in an array. @param a the array @return the most frequent value in a */ public { int int for { static int findMostFrequent(int[] a) mostFrequent = 0; highestFrequency = -1; (int i = 0; i < a.length; i++) int frequency = count(a, a[i]); if (frequency > highestFrequency) { highestFrequency = frequency; mostFrequent = a[i]; } } return mostFrequent; } } ---------------------------------------------------------import java.util.Arrays; /** This program demonstrates finding the most frequent value in an array of random values. */ public class MostFrequentDemo { public static void main(String[] args) { int[] a = ArrayUtil.randomIntArray(20, 100); System.out.println(Arrays.toString(a)); int result = FrequentFinder.findMostFrequent(a); System.out.println(result); } } P14.9 import java.util.Arrays; /** This program compares the original and the modified quicksort algorithms. The second one is a little slower. */ public class QuickSortTimer { public static void main(String[] args) © John Wiley & Sons, Inc. All rights reserved. 9 { int length = 10000000; int values = 100000; int[] a = ArrayUtil.randomIntArray(length, values); int[] a2 = Arrays.copyOf(a, a.length); StopWatch timer = new StopWatch(); timer.start(); QuickSorter.sort(a); timer.stop(); if (checkSorted(a)) { System.out.println("Elapsed time: " + timer.getElapsedTime() + " milliseconds"); } else { System.out.println("Error"); } timer.reset(); timer.start(); QuickSorter2.sort(a2); timer.stop(); if (checkSorted(a2)) { System.out.println("Elapsed time: " + timer.getElapsedTime() + " milliseconds"); } else { System.out.println("Error"); } } public static boolean checkSorted(int[] a) { for (int i = 0; i < a.length - 2; i++) { if (a[i] > a[i + 1]) { return false; } } return true; } } -----------------------------------------------/** The sort method of this class sorts an array, using the quick sort algorithm. */ public class QuickSorter { /** Sorts an array, using quick sort. @param a the array to sort */ public static void sort(int[] a) © John Wiley & Sons, Inc. All rights reserved. 10 { sort(a, 0, a.length - 1); } /** Sorts a portion of an array, using quick sort. @param a the array to sort @param from the first index of the portion to be sorted @param to the last index of the portion to be sorted */ public static void sort(int[] a, int from, int to) { if (from >= to) { return; } int p = partition(a, from, to); sort(a, from, p); sort(a, p + 1, to); } /** Partitions a portion of an array. @param a the array to partition @param from the first index of the portion to be partitioned @param to the last index of the portion to be partitioned @return the last index of the first partition */ private static int partition(int[] a, int from, int to) { int pivot = a[from]; int i = from - 1; int j = to + 1; while (i < j) { i++; while (a[i] < pivot) { i++; } j--; while (a[j] > pivot) { j--; } if (i < j) { ArrayUtil.swap(a, i, j); } } return j; } } -----------------------------------------------/** The sort method of this class sorts an array, using the quick sort algorithm with the modified pivot algorithm. */ public class QuickSorter2 { /** Computes the median of 3 values. @param a the first value @param b the first value @param c the first value @return the median of a, b, and c */ public static int med(int a, int b, int c) { © John Wiley & Sons, Inc. All rights reserved. 11 if (a < b) { if (b < c) { return b; } // a else { return Math.max(a, c); } else { if (c < b) { return b; } // c else { return Math.min(a, c); } < b < c } // a < b, c <= b < b <= a } // b < c, b <= a } /** Gets a pivot of a portion of an array, using the BentleyMcIlroy approach. @param a the array to sort @param from the first index of the portion to be sorted @param to the last index of the portion to be sorted @return the pivot to use */ public static int getPivot(int[] a, int from, int to) { int n = to - from + 1; if (n <= 7) { return a[(from + to) / 2]; } else if (n <= 40) { return med(a[from], a[(from + to) / 2], a[to]); } else { int[] v = new int[9]; for (int i = 0; i < v.length; i++) { v[i] = a[from + i * (n - 1) / 8]; } return med(med(v[0], v[1], v[2]), med(v[3], v[4], v[5]), med(v[6], v[7], v[8])); } } /** Sorts an array, using quicksort. @param a the array to sort */ public static void sort(int[] a) { sort(a, 0, a.length - 1); } /** Sorts a portion of an array, using quicksort. @param a the array to sort @param from the first index of the portion to be sorted @param to the last index of the portion to be sorted © John Wiley & Sons, Inc. All rights reserved. 12 */ public static void sort(int[] a, int from, int to) { if (from >= to) { return; } int p = partition(a, from, to); sort(a, from, p); sort(a, p + 1, to); } /** Partitions a portion of an array. @param a the array to partition @param from the first index of the portion to be partitioned @param to the last index of the portion to be partitioned @return the last index of the first partition */ private static int partition(int[] a, int from, int to) { int pivot = getPivot(a, from, to); int i = from - 1; int j = to + 1; while (i < j) { i++; while (a[i] < pivot) { i++; } j--; while (a[j] > pivot) { j--; } if (i < j) { ArrayUtil.swap(a, i, j); } } return j; } } -----------------------------------------------/** A stopwatch accumulates time when it is running. You can repeatedly start and stop the stopwatch. You can use a stopwatch to measure the running time of a program. */ public class StopWatch { private long elapsedTime; private long startTime; private boolean isRunning; /** Constructs a stopwatch that is in the stopped state and has no time accumulated. */ public StopWatch() { reset(); } /** Starts the stopwatch. Time starts accumulating now. */ public void start() © John Wiley & Sons, Inc. All rights reserved. 13 { if (isRunning) { return; } isRunning = true; startTime = System.currentTimeMillis(); } /** Stops the stopwatch. Time stops accumulating and is is added to the elapsed time. */ public void stop() { if (!isRunning) { return; } isRunning = false; long endTime = System.currentTimeMillis(); elapsedTime = elapsedTime + endTime - startTime; } /** Returns the total elapsed time. @return the total elapsed time */ public long getElapsedTime() { if (isRunning) { long endTime = System.currentTimeMillis(); return elapsedTime + endTime - startTime; } else { return elapsedTime; } } /** Stops the watch and resets the elapsed time to 0. */ public void reset() { elapsedTime = 0; isRunning = false; } } -----------------------------------------------import java.util.Random; /** This class contains utility methods for array manipulation. */ public class ArrayUtil { private static Random generator = new Random(); /** © John Wiley & Sons, Inc. All rights reserved. 14 Creates an array filled with random values. @param length the length of the array @param n the number of possible random values @return an array filled with length numbers between 0 and n - 1 */ public static int[] randomIntArray(int length, int n) { int[] a = new int[length]; for (int i = 0; i < a.length; i++) { a[i] = generator.nextInt(n); } return a; } /** Swaps two entries of an array. @param a the array @param i the first position to swap @param j the second position to swap */ public static void swap(int[] a, int i, int j) { int temp = a[i]; a[i] = a[j]; a[j] = temp; } } P14.10 import java.util.Arrays; /** This program compares the original and the modified quicksort algorithms, on an array with many identical elements. The second one is about two times faster. */ public class QuickSortTimer { public static void main(String[] args) { int length = 10000000; int values = 100; int[] a = ArrayUtil.randomIntArray(length, values); int[] a2 = Arrays.copyOf(a, a.length); StopWatch timer = new StopWatch(); timer.start(); QuickSorter.sort(a); timer.stop(); if (checkSorted(a)) { System.out.println("Elapsed time: " © John Wiley & Sons, Inc. All rights reserved. 15 + timer.getElapsedTime() + " milliseconds"); } else { System.out.println("Error"); } timer.reset(); timer.start(); QuickSorter2.sort(a2); timer.stop(); if (checkSorted(a2)) { System.out.println("Elapsed time: " + timer.getElapsedTime() + " milliseconds"); } else { System.out.println("Error"); } } public static boolean checkSorted(int[] a) { for (int i = 0; i < a.length - 2; i++) { if (a[i] > a[i + 1]) { return false; } } return true; } } -----------------------------------------------/** The sort method of this class sorts an array, using the quick sort algorithm. */ public class QuickSorter { /** Sorts an array, using quick sort. @param a the array to sort */ public static void sort(int[] a) { sort(a, 0, a.length - 1); } /** Sorts a portion of an array, using quick sort. @param a the array to sort @param from the first index of the portion to be sorted @param to the last index of the portion to be sorted */ public static void sort(int[] a, int from, int to) { © John Wiley & Sons, Inc. All rights reserved. 16 if (from >= to) { return; } int p = partition(a, from, to); sort(a, from, p); sort(a, p + 1, to); } /** Partitions a portion of an array. @param a the array to partition @param from the first index of the portion to be partitioned @param to the last index of the portion to be partitioned @return the last index of the first partition */ private static int partition(int[] a, int from, int to) { int pivot = a[from]; int i = from - 1; int j = to + 1; while (i < j) { i++; while (a[i] < pivot) { i++; } j--; while (a[j] > pivot) { j--; } if (i < j) { ArrayUtil.swap(a, i, j); } } return j; } } -----------------------------------------------/** The sort method of this class sorts an array, using the quick sort algorithm. */ public class QuickSorter2 { /** Sorts an array, using quick sort. @param a the array to sort */ public static void sort(int[] a) { sort(a, 0, a.length - 1); } /** Sorts a portion of an array, using quick sort. @param a the array to sort @param from the first index of the portion to be sorted @param to the last index of the portion to be sorted */ public static void sort(int[] a, int from, int to) { if (from >= to) { return; } int[] p = partition(a, from, to); sort(a, from, p[0]); sort(a, p[1], to); © John Wiley & Sons, Inc. All rights reserved. 17 } /** Partitions a portion of an array. @param a the array to partition @param from the first index of the portion to be partitioned @param to the last index of the portion to be partitioned @return an array containing the last index of the < partition and the first index of the > partition */ public static int[] partition(int[] a, int from, int to) { int pivot = a[from]; int i = from; int j = to + 1; int i0 = i; // last index at left == pivot int j0 = j; // first index at right == pivot while (i < j) { i++; while (i < j && a[i] <= pivot) { if (a[i] == pivot) { i0++; a[i] = a[i0]; } i++; } j--; while (i <= j && a[j] >= pivot) { if (a[j] == pivot) { j0--; a[j] = a[j0]; } j--; } if (i < j) { ArrayUtil.swap(a, i, j); } } /* [ = from | i0 < | > | j = j0 ] to */ int int int int equalLeft = i0 - from + 1; smaller = j - i0; larger = j0 - j - 1; equalRight = to - j0 + 1; for (int k = i0 + 1; k <= j; k++) { a[k - equalLeft] = a[k]; } for (int k = j0 - 1; k > j; k--) { a[k + equalRight] = a[k]; } for (int k = 0; k < equalLeft + equalRight; k++) © John Wiley & Sons, Inc. All rights reserved. 18 { a[from + smaller + k] = pivot; } return new int[] { from + smaller - 1, to - larger + 1 }; } } -----------------------------------------------/** A stopwatch accumulates time when it is running. You can repeatedly start and stop the stopwatch. You can use a stopwatch to measure the running time of a program. */ public class StopWatch { private long elapsedTime; private long startTime; private boolean isRunning; /** Constructs a stopwatch that is in the stopped state and has no time accumulated. */ public StopWatch() { reset(); } /** Starts the stopwatch. Time starts accumulating now. */ public void start() { if (isRunning) { return; } isRunning = true; startTime = System.currentTimeMillis(); } /** Stops the stopwatch. Time stops accumulating and is is added to the elapsed time. */ public void stop() { if (!isRunning) { return; } isRunning = false; long endTime = System.currentTimeMillis(); elapsedTime = elapsedTime + endTime - startTime; } /** Returns the total elapsed time. @return the total elapsed time */ public long getElapsedTime() © John Wiley & Sons, Inc. All rights reserved. 19 { if (isRunning) { long endTime = System.currentTimeMillis(); return elapsedTime + endTime - startTime; } else { return elapsedTime; } } /** Stops the watch and resets the elapsed time to 0. */ public void reset() { elapsedTime = 0; isRunning = false; } } -----------------------------------------------import java.util.Random; /** This class contains utility methods for array manipulation. */ public class ArrayUtil { private static Random generator = new Random(); /** Creates an array filled with random values. @param length the length of the array @param n the number of possible random values @return an array filled with length numbers between 0 and n - 1 */ public static int[] randomIntArray(int length, int n) { int[] a = new int[length]; for (int i = 0; i < a.length; i++) { a[i] = generator.nextInt(n); } return a; } /** Swaps two entries of an array. @param a the array @param i the first position to swap @param j the second position to swap */ © John Wiley & Sons, Inc. All rights reserved. 20 public static void swap(int[] a, int i, int j) { int temp = a[i]; a[i] = a[j]; a[j] = temp; } } P14.11 public class Radix { /** Sorts an array using radix sort. @param a an array of non-negative integers from 0- 999 */ public static void radixsort(int[] a) { int n = a.length; // Gets largest value in array int max = a[0]; for (int i = 0; i < n; i++) { if (a[i] > max) { max = a[i]; } } // Gets number of digits in largest value int c = 0; while (max > 0) { c++; max = max / 10; } // Make ten new temporary arrays and fill them with -1 int[] zero = new int[n]; int[] one = new int[n]; int[] two = new int[n]; int[] three = new int[n]; int[] four = new int[n]; int[] five = new int[n]; int[] six = new int[n]; int[] seven = new int[n]; int[] eight = new int[n]; int[] nine = new int[n]; for (int i = 0; i < n; i++) { zero[i] = -1; one[i] = -1; two[i] = -1; three[i] = -1; four[i] = -1; five[i] = -1; six[i] = -1; © John Wiley & Sons, Inc. All rights reserved. 21 seven[i] = -1; eight[i] = -1; nine[i] = -1; } // Loop times number of digits int k = 1; int temp; for (int l = 0; l < c; l++) { // Copy values into temporary array for (int i = 0; i < n; i++) { temp = (a[i] / k) % 10; if (temp == 0) { zero[i] = a[i]; } if (temp == 1) { one[i] = a[i]; } if (temp == 2) { two[i] = a[i]; } if (temp == 3) { three[i] = a[i]; } if (temp == 4) { four[i] = a[i]; } if (temp == 5) { five[i] = a[i]; } if (temp == 6) { six[i] = a[i]; } if (temp == 7) { seven[i] = a[i]; } if (temp == 8) { eight[i] = a[i]; } if (temp == 9) { nine[i] = a[i]; } } // Increment k for next pass k = k * 10; // Copy values back into a int pos = 0; int i = 0; for (i = 0; i < n; i++) { if (zero[i] != -1) { a[pos] = zero[i]; pos++; } } for (i = 0; i < n; i++) { if (one[i] != -1) { a[pos] = one[i]; pos++; } } for (i = 0; i < n; i++) { if (two[i] != -1) { a[pos] = two[i]; pos++; } } for (i = 0; i < n; i++) { if (three[i] != -1) { a[pos] = three[i]; pos++; } } for (i = 0; i < n; i++) { if (four[i] != -1) { a[pos] = four[i]; pos++; } } for (i = 0; i < n; i++) { if (five[i] != -1) { a[pos] = five[i]; pos++; } } for (i = 0; i < n; i++) © John Wiley & Sons, Inc. All rights reserved. 22 { if (six[i] != -1) { a[pos] = six[i]; pos++; } } for (i = 0; i < n; i++) { if (seven[i] != -1) { a[pos] = seven[i]; pos++; } } for (i = 0; i < n; i++) { if (eight[i] != -1) { a[pos] = eight[i]; pos++; } } for (i = 0; i < n; i++) { if (nine[i] != -1) { a[pos] = nine[i]; pos++; } } // Refill temporary array with -1 for (i = 0; i < n; i++) { zero[i] = -1; one[i] = -1; two[i] = -1; three[i] = -1; four[i] = -1; five[i] = -1; six[i] = -1; seven[i] = -1; eight[i] = -1; nine[i] = -1; } } } } P14.12 /** This class performs a radix sort on an array of integer values from 0 to 999. /** Sorts an array using radix sort. @param a an array of non-negative integers @param n the length of the array */ public class Radix { public static void radixsort(int[] a) { int n = a.length; // Gets largest value in array int max = a[0]; for (int i = 0; i < n; i++) { © John Wiley & Sons, Inc. All rights reserved. 23 if (a[i] > max) { max = a[i]; } } // Gets number of digits in largest value int c = 0; while (max > 0) { c++; max = max / 10; } // Make int[][] int i = int j = a new temporary array and fill it with -999 b = new int[10][a.length]; 1; 1; for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { b[i][j] = -999; } } // Loop times number of digits int k = 1; int temp; for (int l = 0; l < c; l++) { // Copy values into temporary array for (j = 0; j < n; j++) { temp = (a[j] / k) % 10; b[temp][j] = a[j]; } // Increment k for next pass k = k * 10; // Copy values back into a int pos = 0; for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { if (b[i][j] != -999) { a[pos++] = b[i][j]; } } } // Refill temporary array with -999 for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { b[i][j] = -999; } } } © John Wiley & Sons, Inc. All rights reserved. 24 } } P14.13 /** This class performs a radix sort on an array of integer values. public class Radix { /** Sorts an array using radix sort. @param a an array of integers */ public static void radixsort(int[] a) { int n = a.length; // Gets largest value in array int max = a[0]; for (int i = 0; i < n; i++) { if (Math.abs(a[i]) > max) { max = a[i]; } } // Gets number of digits in largest value int c = 0; while (max > 0) { c++; max = max / 10; } // Make int[][] int[][] int i = int j = two new temporary arrays and fill them with -1000 b = new int[10][n]; neg = new int[10][n]; 1; 1; for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { b[i][j] = -1000; neg[i][j] = -1000; } } // Loop times number of digits int k = 1; int temp; for (int l = 0; l < c; l++) { // Copy values into temporary arrays for (j = 0; j < n; j++) © John Wiley & Sons, Inc. All rights reserved. 25 { temp = (a[j] / k) % 10; if (temp < 0) { neg[-temp][j] = a[j]; } else { b[temp][j] = a[j]; } } // Increment k for next pass k = k * 10; // Copy values back into a int pos = 0; for (i = 9; i >= 0; i--) { for (j = n - 1; j >= 0; j--) { if (neg[i][j] != -1000) { a[pos] = neg[i][j]; pos++; } } } for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { if (b[i][j] != -1000) { a[pos] = b[i][j]; pos++; } } } // Refill temporary array with -1000 for (i = 0; i < 10; i++) { for (j = 0; j < n; j++) { b[i][j] = -1000; neg[i][j] = -1000; } } } } } P14.14 © John Wiley & Sons, Inc. All rights reserved. 26 import java.util.Comparator; public class ReverseCountryComparator implements Comparator<Country> { public int compare(Country a, Country b) { if (a.getArea() > b.getArea() { return -1; } else if (a.getArea() == b.getArea() { return 0; } else { return 1; } } } P14.15 /** A class for executing binary searches through an array. */ public class BinarySearcher { /** Finds a value in a range of a sorted array, using the binary search algorithm. @param a the array in which to search @param low the low index of the range @param high the high index of the range @param value the value to find @return the index at which the value occurs, or -k - 1 if it does not occur in the array */ public static int search(int[] a, int low, int high, int value) { if (low <= high) { int mid = (low + high) / 2; if (a[mid] == value) { return mid; } else if (a[mid] < value ) { return search(a, mid + 1, high, value); } else { return search(a, low, mid - 1, value); } } else { return -low - 1; } } } © John Wiley & Sons, Inc. All rights reserved. 27 P14.16 /** The sort method of this class sorts an array, using the merge sort algorithm. */ public class MergeSorter { /** Sorts an array, using a non-recursive merge sort algorithm. @param a the array to sort */ public static void sort(int[] a) { int size = 1; int from = 0; int to = a.length - 1; while (size < to - from) { for (int i = 0; i + 2 * size <= to - from + 1; i = i + 2 * size) { merge(from + i, from + i + size - 1, from + i + 2 * size - 1, a); } size = 2 * size; } } public static void merge(int from, int mid, int to, int[] a) { int n = to - from + 1; // Size of the range to be merged // Merge both halves into a temporary array b int[] b = new int[n]; int i1 = from; // Next element to consider in the first half int i2 = mid + 1; // Next element to consider in the second half int j = 0; // Next open position in b // As long as neither i1 nor i2 past the end, move // the smaller element into b while (i1 <= mid && i2 <= to) { if (a[i1] < a[i2]) { b[j] = a[i1]; i1++; } else { b[j] = a[i2]; © John Wiley & Sons, Inc. All rights reserved. 28 i2++; } j++; } // Note that only one of the two while loops // below is executed // Copy any remaining entries of the first half while (i1 <= mid) { b[j] = a[i1]; i1++; j++; } // Copy any remaining entries of the second half while (i2 <= to) { b[j] = a[i2]; i2++; j++; } // Copy back from the temporary array for (j = 0; j < n; j++) { a[from + j] = b[j]; } } } P14.17 /** This class sorts an array, using the merge sort algorithm nonrecursively. */ public class MergeSorter { public static void sort(int[] a) { int length = 1; // The size of the sorted areas; a power of 2 while (length <= a.length) { int start = 0; // sort starts at the beginning of the array while (start + 2 * length <= a.length) { // Merge all adjacent areas of size length // into sorted areas of size 2 * length merge(start, start + length - 1, start + 2 * length – 1, a); start = start + 2 * length; } © John Wiley & Sons, Inc. All rights reserved. 29 // If there were some elements that weren't sorted in // this pass, then sort them now if (start + length <= a.length) { merge(start, start + length - 1, a.length – 1, a); } length = length * 2; // Double the size of the next sort areas start = 0; // Start the sort pass at the beginning of the array } } public static void merge(int from, int mid, int to, int[] a) { int n = to - from + 1; // Size of the range to be merged // Merge both halves into a temporary array b int[] b = new int[n]; int i1 = from; // Next element to consider in the first half int i2 = mid + 1; // Next element to consider in the second half int j = 0; // Next open position in b // As long as neither i1 nor i2 past the end, move // the smaller element into b while (i1 <= mid && i2 <= to) { if (a[i1] < a[i2]) { b[j] = a[i1]; i1++; } else { b[j] = a[i2]; i2++; } j++; } // Note that only one of the two while loops // below is executed // Copy any remaining entries of the first half while (i1 <= mid) { b[j] = a[i1]; i1++; j++; } // Copy any remaining entries of the second half while (i2 <= to) { b[j] = a[i2]; © John Wiley & Sons, Inc. All rights reserved. 30 i2++; j++; } // Copy back from the temporary array for (j = 0; j < n; j++) { a[from + j] = b[j]; } } } P14.18 import java.util.Arrays; /** This class sorts an array, using a modified insertion sort algorithm. */ public class InsertionSorter { public static void sort(int[] a) { for (int i = 1; i < a.length; i++) { int next = a[i]; int index = search(next, 0, i – 1, a); if (index < 0) index = -index - 1; // Move all larger elements up int j = i; while (j > index) { a[j] = a[j - 1]; j--; } // Insert the element a[index] = next; } } private int search(int v, int low, int high, a) { while (low <= high) { int mid = (low + high) / 2; int diff = a[mid] - v; if (diff == 0) // a[mid] == v { return mid; } else if (diff < 0) // a[mid] < v © John Wiley & Sons, Inc. All rights reserved. 31 { low = mid + 1; } else { high = mid - 1; } } return -low - 1; } } P14.19 /** A person. */ public class Person implements Comparable { private String name; /** Construct a Person object. @param aName the name of the person */ public Person(String aName) { name = aName; } public int compareTO(Object otherObject) { Person other = (Person) otherObject; if (name.compareTO(other.name) < 0) { return -1; } else if (name.compareTO(other.name) == 0) { return 0; } else { return 1; } } /** Gets the name of the person. @return the name of the person */ public String getName() { return name; } © John Wiley & Sons, Inc. All rights reserved. 32 public String toString() { return "Person[name=" + name + "]"; } } ---------------------------------------import java.util.Scanner; import java.util.Arrays; /** This class tests the Person class. */ public class PersonDemo { public static void main(String[] args) { int count = 0; Scanner in = new Scanner(System.in); boolean done = false; Person first = null; Person last = null; while (!done) { System.out.println("Please enter the person's name or a blank line to quit"); String name = in.nextLine(); if (name.equals("")) { done = true; } else { Person p = new Person(name); if (first == null) { first = last = p; } else { if (first.compareTo(p) > 0) { first = p; } if (last. compareTo(p) < 0) { last = p; } } } } System.out.println("First: " + first); System.out.println("Last: " + last); } } P14.20 import java.util.Comparator; public class StringLengthComparator implements Comparator<String> { public int compare(String first, String second) © John Wiley & Sons, Inc. All rights reserved. 33 { int d = first.length() - second.length(); if (d < 0) { return -1; } else if (d > 0) { return 1; } else { return 0; } } } -------------------------------------------import java.util.ArrayList; import java.util.Collections; import java.util.Scanner; /** Sort an array list of strings by increasing length. */ public class StringSortDemo { public static void main(String[] args) { ArrayList<String> list = new ArrayList<String>(); Scanner in = new Scanner(System.in); boolean done = false; while (!done) { System.out.println("Enter a string or a blank line to quit"); String input = in.nextLine(); if (input.equals("")) { done = true; } else { list.add(input); } } Collections.sort(list, new StringLengthComparator()); System.out.println(list); } } P14.21 import java.util.Comparator; public class StringLengthLexComparator implements Comparator<String> { public int compare(String first, String second) { int d = first.length() - second.length(); if (d < 0) { return -1; } else if (d > 0) { return 1; } else { return 0; } } } -------------------------------------------- © John Wiley & Sons, Inc. All rights reserved. 34 import java.util.ArrayList; import java.util.Collections; import java.util.Scanner; /** Sort an array list of strings by increasing length. */ public class StringSortDemo { public static void main(String[] args) { ArrayList<String> list = new ArrayList<String>(); Scanner in = new Scanner(System.in); boolean done = false; while (!done) { System.out.println("Enter a string or a blank line to quit"); String input = in.nextLine(); if (input.equals("")) { done = true; } else { list.add(input); } } Collections.sort(list, new StringLengthLexComparator()); System.out.println(list); } } © John Wiley & Sons, Inc. All rights reserved. 35