package com.interview.algorithms.string; /** * Key-indexed counting uses ~ 11 N + 4 R array accesses to sort * N items whose keys are integers between 0 and R - 1. * It's a stable sort, and uses extra space proportional to N + R. * * Assumption. Keys are integers between 0 and R - 1. * Implication. Can use key as an array index. * * @author stefanie * */ public class C11_16_KeyIndexedSorter { public static int CHARSET = 26; public int R; public C11_16_KeyIndexedSorter(int r) { super(); R = r; } public void sort(char[] charlist){ int N = charlist.length; int[] count = new int[R+1]; char[] aux = new char[N]; //Count frequencies of each letter using key as index. for (int i = 0; i < N; i++){ int index = charlist[i] - 'A' + 1; count[index]++; } //Compute frequency cumulates which specify destinations. for (int r = 0; r < R; r++) count[r+1] += count[r]; //Access cumulates using key as index to move items. for (int i = 0; i < N; i++){ int index = charlist[i] - 'A'; aux[count[index]++] = charlist[i]; } //Copy back into original array. for (int i = 0; i < N; i++) charlist[i] = aux[i]; } /** * sort a string by index, used in LSD Sorter * @param strlist * @param index */ public void sort(String[] strlist, String[] aux, int index){ int N = strlist.length; int[] count = new int[R+1]; //Count frequencies of each letter using key as index. for (int i = 0; i < N; i++){ int k = strlist[i].charAt(index) - 'A' + 1; count[k]++; } //Compute frequency cumulates which specify destinations. for (int r = 0; r < R; r++) count[r+1] += count[r]; //Access cumulates using key as index to move items. for (int i = 0; i < N; i++){ int k = strlist[i].charAt(index) - 'A'; aux[count[k]++] = strlist[i]; } //Copy back into original array. for (int i = 0; i < N; i++) strlist[i] = aux[i]; } /** * sort the string by start and end index, used in MSD Sorter * @param strlist */ public void sort(String[] strlist, String[] aux, int lo, int hi, int d){ if (hi <= lo) return; int[] count = new int[R+2]; for (int i = lo; i <= hi; i++){ count[strlist[i].charAt(d) - 'A' + 2]++; } for (int r = 0; r < R+1; r++) count[r+1] += count[r]; for (int i = lo; i <= hi; i++) aux[count[strlist[i].charAt(d) - 'A' + 1]++] = strlist[i]; for (int i = lo; i <= hi; i++) strlist[i] = aux[i - lo]; for (int r = 0; r < R; r++) sort(strlist, aux, lo + count[r], lo + count[r+1] - 1, d+1); } }