日撸 Java 三百行(41-50天,查找与排序)

目录

总述
01-10天,基本语法
11-20天,线性数据结构
21-30天,树与二叉树
31-40天,图
41-50天,查找与排序
51-60天,kNN 与 NB
61-70天,决策树与集成学习
71-80天,BP 神经网络
81-90天,CNN 卷积神经网络

第 41 天: 顺序查找与折半查找

  1. 顺序查找使用岗哨可以节约一半的时间. 为此, 第 0 个位置不可以放有意义的数据, 即有效数据只有 length - 1 个.
  2. 顺序查找时间复杂度为 O ( n ) O(n) O(n).
  3. 折半查找时间复杂度为 O ( log ⁡ n ) O(\log n) O(logn).
  4. 书上为简化起见, 只关注键. 这里使用键值对来表示一条完整的数据. 实际应用中可以把 content 改成任何想要的数据类型.
  5. 102 行是一个空语句. 这里提供了一种更简洁的写法, 可以把 101-103 并作一行 (100行).
  6. for 语句这些的花括号, 本意是将一个代码块当一条语句来处理, for 循环里面只有一条语句, 可以将花括号省略掉. 只是我个人喜欢将其保留, 以保持一致性. 例如: 66-68 行.
package datastructure.search;

/**
 * Data array for searching and sorting algorithms.
 * 
 * @author Fan Min minfanphd@163.com.
 */
public class DataArray {
	/**
	 * An inner class for data nodes. The text book usually use an int value to
	 * represent the data. I would like to use a key-value pair instead.
	 */
	class DataNode {
		/**
		 * The key.
		 */
		int key;

		/**
		 * The data content.
		 */
		String content;

		/**
		 *********************
		 * The first constructor.
		 *********************
		 */
		DataNode(int paraKey, String paraContent) {
			key = paraKey;
			content = paraContent;
		}// Of the first constructor

		/**
		 *********************
		 * Overrides the method claimed in Object, the superclass of any class.
		 *********************
		 */
		public String toString() {
			return "(" + key + ", " + content + ") ";
		}// Of toString
	}// Of class DataNode

	/**
	 * The data array.
	 */
	DataNode[] data;

	/**
	 * The length of the data array.
	 */
	int length;

	/**
	 *********************
	 * The first constructor.
	 * 
	 * @param paraKeyArray     The array of the keys.
	 * @param paraContentArray The array of contents.
	 *********************
	 */
	public DataArray(int[] paraKeyArray, String[] paraContentArray) {
		length = paraKeyArray.length;
		data = new DataNode[length];

		for (int i = 0; i < length; i++) {
			data[i] = new DataNode(paraKeyArray[i], paraContentArray[i]);
		} // Of for i
	}// Of the first constructor

	/**
	 *********************
	 * Overrides the method claimed in Object, the superclass of any class.
	 *********************
	 */
	public String toString() {
		String resultString = "I am a data array with " + length + " items.\r\n";
		for (int i = 0; i < length; i++) {
			resultString += data[i] + " ";
		} // Of for i

		return resultString;
	}// Of toString

	/**
	 *********************
	 * Sequential search. Attention: It is assume that the index 0 is NOT used.
	 * 
	 * @param paraKey The given key.
	 * @return The content of the key.
	 *********************
	 */
	public String sequentialSearch(int paraKey) {
		data[0].key = paraKey;

		int i;
		// Note that we do not judge i >= 0 since data[0].key = paraKey.
		// In this way the runtime is saved about 1/2.
		// This for statement is equivalent to 
		//for (i = length - 1; data[i].key != paraKey; i--);
		for (i = length - 1; data[i].key != paraKey; i--) {
			;
		}//Of for i
		return data[i].content;
	}// Of sequentialSearch

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void sequentialSearchTest() {
		int[] tempUnsortedKeys = { -1, 5, 3, 6, 10, 7, 1, 9 };
		String[] tempContents = { "null", "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		System.out.println("Search result of 10 is: " + tempDataArray.sequentialSearch(10));
		System.out.println("Search result of 5 is: " + tempDataArray.sequentialSearch(5));
		System.out.println("Search result of 4 is: " + tempDataArray.sequentialSearch(4));
	}// Of sequentialSearchTest

	/**
	 *********************
	 * Binary search. Attention: It is assume that keys are sorted in ascending
	 * order.
	 * 
	 * @param paraKey The given key.
	 * @return The content of the key.
	 *********************
	 */
	public String binarySearch(int paraKey) {
		int tempLeft = 0;
		int tempRight = length - 1;
		int tempMiddle = (tempLeft + tempRight) / 2;

		while (tempLeft <= tempRight) {
			tempMiddle = (tempLeft + tempRight) / 2;
			if (data[tempMiddle].key == paraKey) {
				return data[tempMiddle].content;
			} else if (data[tempMiddle].key <= paraKey) {
				tempLeft = tempMiddle + 1;
			} else {
				tempRight = tempMiddle - 1;
			}
		} // Of while

		// Not found.
		return "null";
	}// Of binarySearch

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void binarySearchTest() {
		int[] tempSortedKeys = { 1, 3, 5, 6, 7, 9, 10 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempSortedKeys, tempContents);

		System.out.println(tempDataArray);

		System.out.println("Search result of 10 is: " + tempDataArray.binarySearch(10));
		System.out.println("Search result of 5 is: " + tempDataArray.binarySearch(5));
		System.out.println("Search result of 4 is: " + tempDataArray.binarySearch(4));
	}// Of binarySearchTest
	
	/**
	 *********************
	 * The entrance of the program.
	 * 
	 * @param args Not used now.
	 *********************
	 */
	public static void main(String args[]) {
		System.out.println("\r\n-------sequentialSearchTest-------");
		sequentialSearchTest();

		System.out.println("\r\n-------binarySearchTest-------");
		binarySearchTest();
	}// Of main

}// Of class DataArray

第 42 天: 哈希表

  1. 神奇、实用、粗暴的方法. 空间换时间.
  2. 保证空间足够.
  3. 在构造方法中装入数据. 自己可以写代码增加数据.
  4. 使用 (最简单的) 除数取余法获得数据存放地址 (下标).
  5. 使用 (最简单的) 顺移位置法解决冲突.
  6. 搜索的时间复杂度仅与冲突概率相关, 间接地就与装填因子相关. 如果空间很多, 可以看出时间复杂度为 O ( 1 ) O(1) O(1).
	/**
	 *********************
	 * The second constructor. For Hash code only. It is assumed that
	 * paraKeyArray.length <= paraLength.
	 * 
	 * @param paraKeyArray     The array of the keys.
	 * @param paraContentArray The array of contents.
	 * @param paraLength       The space for the Hash table.
	 *********************
	 */
	public DataArray(int[] paraKeyArray, String[] paraContentArray, int paraLength) {
		// Step 1. Initialize.
		length = paraLength;
		data = new DataNode[length];

		for (int i = 0; i < length; i++) {
			data[i] = null;
		} // Of for i

		// Step 2. Fill the data.
		int tempPosition;

		for (int i = 0; i < paraKeyArray.length; i++) {
			// Hash.
			tempPosition = paraKeyArray[i] % paraLength;

			// Find an empty position
			while (data[tempPosition] != null) {
				tempPosition = (tempPosition + 1) % paraLength;
				System.out.println("Collision, move forward for key " + paraKeyArray[i]);
			} // Of while

			data[tempPosition] = new DataNode(paraKeyArray[i], paraContentArray[i]);
		} // Of for i
	}// Of the second constructor

	/**
	 *********************
	 * Hash search.
	 * 
	 * @param paraKey The given key.
	 * @return The content of the key.
	 *********************
	 */
	public String hashSearch(int paraKey) {
		int tempPosition = paraKey % length;
		while (data[tempPosition] != null) {
			if (data[tempPosition].key == paraKey) {
				return data[tempPosition].content;
			} // Of if
			System.out.println("Not this one for " + paraKey);
			tempPosition = (tempPosition + 1) % length;
		} // Of while

		return "null";
	}// Of hashSearch

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void hashSearchTest() {
		int[] tempUnsortedKeys = { 16, 33, 38, 69, 57, 95, 86 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents, 19);

		System.out.println(tempDataArray);

		System.out.println("Search result of 95 is: " + tempDataArray.hashSearch(95));
		System.out.println("Search result of 38 is: " + tempDataArray.hashSearch(38));
		System.out.println("Search result of 57 is: " + tempDataArray.hashSearch(57));
		System.out.println("Search result of 4 is: " + tempDataArray.hashSearch(4));
	}// Of hashSearchTest

	/**
	 *********************
	 * The entrance of the program.
	 * 
	 * @param args Not used now.
	 *********************
	 */
	public static void main(String args[]) {
		System.out.println("\r\n-------sequentialSearchTest-------");
		sequentialSearchTest();

		System.out.println("\r\n-------binarySearchTest-------");
		binarySearchTest();

		System.out.println("\r\n-------hashSearchTest-------");
		hashSearchTest();
	}// Of main

第 43 天: 插入排序

  1. 插入排序是简单直接的排序方式之一. 代码非常短.
  2. 每次保证前 i 个数据是有序的.
  3. 先做简单的事情 (第 1 轮最多有 1 次移动), 再做麻烦的事情 (最后一轮最多有 n − 1 n - 1 n1 次移动).
  4. 下标 0 的数据为岗哨, 与 41 天内容同理. 比其它排序方式多用一个空间.
  5. 又见 this.
  6. tempNode 只分配了引用 (指针) 的空间, 并未 new.
	/**
	 *********************
	 * Insertion sort. data[0] does not store a valid data. data[0].key should
	 * be smaller than any valid key.
	 *********************
	 */
	public void insertionSort() {
		DataNode tempNode;
		int j;
		for (int i = 2; i < length; i++) {
			tempNode = data[i];
			
			//Find the position to insert.
			//At the same time, move other nodes.
			for (j = i - 1; data[j].key > tempNode.key; j--) {
				data[j + 1] = data[j];
			} // Of for j
			
			//Insert.
			data[j + 1] = tempNode;
			
			System.out.println("Round " + (i - 1));
			System.out.println(this);
		} // Of for i
	}// Of insertionSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void insertionSortTest() {
		int[] tempUnsortedKeys = { -100, 5, 3, 6, 10, 7, 1, 9 };
		String[] tempContents = { "null", "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.insertionSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of insertionSortTest

第 44 天: 希尔排序

  1. 多达 4 重循环, 但时间复杂度只有 O ( n 2 ) O(n^2) O(n2). 多次排序反正减少了平均排序时间. 神奇的脑回路.
  2. 有了昨天的程序铺垫, 本程序写起来也不难.
  3. 岗哨的个数与最初的步长相关, 我们的程序中为 5. 简便起见我就没用了.
  4. 可以改变 tempJumpArray.
  5. 测试用例多用了几个数据, 便于观察.
	/**
	 *********************
	 * Shell sort. We do not use sentries here because too many of them are needed.
	 *********************
	 */
	public void shellSort() {
		DataNode tempNode;
		int[] tempJumpArray = { 5, 3, 1 };
		int tempJump;
		int p;
		for (int i = 0; i < tempJumpArray.length; i++) {
			tempJump = tempJumpArray[i];
			for (int j = 0; j < tempJump; j++) {
				for (int k = j + tempJump; k < length; k += tempJump) {
					tempNode = data[k];
					// Find the position to insert.
					// At the same time, move other nodes.
					for (p = k - tempJump; p >= 0; p -= tempJump) {
						if (data[p].key > tempNode.key) {
							data[p + tempJump] = data[p];
						} else {
							break;
						} // Of if
					} // Of for p

					// Insert.
					data[p + tempJump] = tempNode;
				} // Of for k
			} // Of for j
			System.out.println("Round " + i);
			System.out.println(this);
		} // Of for i
	}// Of shellSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void shellSortTest() {
		int[] tempUnsortedKeys = { 5, 3, 6, 10, 7, 1, 9, 12, 8, 4 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while", "throw", "until", "do" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.shellSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of shellSortTest

第 45 天: 冒泡排序

  1. 每次确定当前最大值, 也就是确定一个位置的数据.
  2. 仅交换相邻数据.
  3. 如果某一趟没有交换, 就表示数据已经有序 (早熟, premature), 可以提前结束了.
	/**
	 *********************
	 * Bubble sort.
	 *********************
	 */
	public void bubbleSort() {
		boolean tempSwapped;
		DataNode tempNode;
		for (int i = length - 1; i > 0; i--) {
			tempSwapped = false;
			for (int j = 0; j < i; j++) {
				if (data[j].key > data[j + 1].key) {
					// Swap.
					tempNode = data[j + 1];
					data[j + 1] = data[j];
					data[j] = tempNode;

					tempSwapped = true;
				} // Of if
			} // Of for j

			// No swap in this round. The data are already sorted.
			if (!tempSwapped) {
				System.out.println("Premature");
				break;
			} // Of if

			System.out.println("Round " + (length - i));
			System.out.println(this);
		} // Of for i
	}// Of bubbleSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void bubbleSortTest() {
		int[] tempUnsortedKeys = { 1, 3, 6, 10, 7, 5, 9 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.bubbleSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of bubbleSortTest

第 46 天: 快速排序

  1. 平均时间复杂度为 O ( n log ⁡ n ) O(n\log n) O(nlogn), 但最坏情况还是 O ( n 2 ) O(n^2) O(n2).
  2. Pivot 应该选 (该子序列的) 最后一个元素.
  3. 递归算法, 每次只能确定 pivot 的位置.
  4. 判断条件 && (tempLeft < tempRight) 不能少.
  5. (data[tempRight].key >= tempPivot) 不能写成 >, 否则出现两个相同 key 时可能出错.
	/**
	 *********************
	 * Quick sort recursively.
	 * 
	 * @param paraStart The start index.
	 * @param paraEnd   The end index.
	 *********************
	 */
	public void quickSortRecursive(int paraStart, int paraEnd) {
		// Nothing to sort.
		if (paraStart >= paraEnd) {
			return;
		} // Of if

		int tempPivot = data[paraEnd].key;
		DataNode tempNodeForSwap;

		int tempLeft = paraStart;
		int tempRight = paraEnd - 1;

		// Find the position for the pivot.
		// At the same time move smaller elements to the left and bigger one to the
		// right.
		while (true) {
			while ((data[tempLeft].key < tempPivot) && (tempLeft < tempRight)) {
				tempLeft++;
			} // Of while

			while ((data[tempRight].key >= tempPivot) && (tempLeft < tempRight)) {
				tempRight--;
			} // Of while

			if (tempLeft < tempRight) {
				// Swap.
				System.out.println("Swapping " + tempLeft + " and " + tempRight);
				tempNodeForSwap = data[tempLeft];
				data[tempLeft] = data[tempRight];
				data[tempRight] = tempNodeForSwap;
			} else {
				break;
			} // Of if
		} // Of while

		// Swap
		if (data[tempLeft].key > tempPivot) {
			tempNodeForSwap = data[paraEnd];
			data[paraEnd] = data[tempLeft];
			data[tempLeft] = tempNodeForSwap;
		} else {
			tempLeft++;
		} // Of if

		System.out.print("From " + paraStart + " to " + paraEnd + ": ");
		System.out.println(this);

		quickSortRecursive(paraStart, tempLeft - 1);
		quickSortRecursive(tempLeft + 1, paraEnd);
	}// Of quickSortRecursive

	/**
	 *********************
	 * Quick sort.
	 *********************
	 */
	public void quickSort() {
		quickSortRecursive(0, length - 1);
	}// Of quickSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void quickSortTest() {
		int[] tempUnsortedKeys = { 1, 3, 12, 10, 5, 7, 9 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.quickSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of quickSortTest

第 47 天: 选择排序

  1. 又是一个基础 (简单) 算法.
  2. 与插入排序不同, 先做最麻烦的, 要进行 n − 1 n - 1 n1 次比较才能获得最小的数据.
  3. 数据一旦被选择并确定位置, 就不再改变.
  4. 做为一种简单算法, 其时间复杂度为 O ( n 2 ) O(n^2) O(n2).
  5. 只需要两个额外的空间来存放最小数据的引用与下标, 因此空间复杂度为 O ( 1 ) O(1) O(1).
	/**
	 *********************
	 * Selection sort. All data are valid.
	 *********************
	 */
	public void selectionSort() {
		DataNode tempNode;
		int tempIndexForSmallest;

		for (int i = 0; i < length - 1; i++) {
			// Initialize.
			tempNode = data[i];
			tempIndexForSmallest = i;
			for (int j = i + 1; j < length; j++) {
				if (data[j].key < tempNode.key) {
					tempNode = data[j];
					tempIndexForSmallest = j;
				} // Of if
			} // Of for j

			// Change the selected one with the current one.
			data[tempIndexForSmallest] = data[i];
			data[i] = tempNode;
		} // Of for i
	}// Of selectionSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void selectionSortTest() {
		int[] tempUnsortedKeys = { 5, 3, 6, 10, 7, 1, 9 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.selectionSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of selectionSortTest

第 48 天: 堆排序

  1. 堆排序可能是排序算法中最难的. 用到了二叉树.
  2. 建初始堆比较费劲.
  3. 调整堆的时间复杂度为 O ( log ⁡ n ) O(\log n) O(logn), 所以总体时间复杂度只有 O ( n log ⁡ n ) O(n \log n) O(nlogn).
  4. 空间复杂度只有 O ( 1 ) O(1) O(1).
	/**
	 *********************
	 * Heap sort. Maybe the most difficult sorting algorithm.
	 *********************
	 */
	public void heapSort() {
		DataNode tempNode;
		// Step 1. Construct the initial heap.
		for (int i = length / 2 - 1; i >= 0; i--) {
			adjustHeap(i, length);
		} // Of for i
		System.out.println("The initial heap: " + this + "\r\n");

		// Step 2. Swap and reconstruct.
		for (int i = length - 1; i > 0; i--) {
			tempNode = data[0];
			data[0] = data[i];
			data[i] = tempNode;

			adjustHeap(0, i);
			System.out.println("Round " + (length - i) + ": " + this);
		} // Of for i
	}// Of heapSort

	/**
	 *********************
	 * Adjust the heap.
	 * 
	 * @param paraStart  The start of the index.
	 * @param paraLength The length of the adjusted sequence.
	 *********************
	 */
	public void adjustHeap(int paraStart, int paraLength) {
		DataNode tempNode = data[paraStart];
		int tempParent = paraStart;
		int tempKey = data[paraStart].key;

		for (int tempChild = paraStart * 2 + 1; tempChild < paraLength; tempChild = tempChild * 2 + 1) {
			// The right child is bigger.
			if (tempChild + 1 < paraLength) {
				if (data[tempChild].key < data[tempChild + 1].key) {
					tempChild++;
				} // Of if
			} // Of if

			System.out.println("The parent position is " + tempParent + " and the child is " + tempChild);
			if (tempKey < data[tempChild].key) {
				// The child is bigger.
				data[tempParent] = data[tempChild];
				System.out.println("Move " + data[tempChild].key + " to position " + tempParent);
				tempParent = tempChild;
			} else {
				break;
			} // Of if
		} // Of for tempChild

		data[tempParent] = tempNode;

		System.out.println("Adjust " + paraStart + " to " + paraLength + ": " + this);
	}// Of adjustHeap

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void heapSortTest() {
		int[] tempUnsortedKeys = { 5, 3, 6, 10, 7, 1, 9 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.heapSort();
		System.out.println("Result\r\n" + tempDataArray);
	}// Of heapSortTest

第 49 天: 归并排序

  1. log ⁡ n \log n logn 轮, 每轮 O ( n ) O(n) O(n) 次拷贝. 因此时间复杂度为 O ( n log ⁡ n ) O(n \log n) O(nlogn).
  2. 空间复杂度为 O ( n ) O(n) O(n). 只需要一行辅助空间.
  3. 全都是在拷贝引用, 而不是数据本身. 这是 Java 的特性.
  4. 里面的两重循环总共只有 O ( n ) O(n) O(n). 这里是分成了若干个小组.
  5. 归并两个有序小组的时候, 用了三个并列的循环.
  6. 涉及分组后尾巴的各种情况, 所以需要相应的 if 语句.
	/**
	 *********************
	 * Merge sort. Results are stored in the member variable data.
	 *********************
	 */
	public void mergeSort() {
		// Step 1. Allocate space.

		int tempRow; // The current row
		int tempGroups; // Number of groups
		int tempActualRow; // Only 0 or 1
		int tempNextRow = 0;
		int tempGroupNumber;
		int tempFirstStart, tempSecondStart, tempSecondEnd;
		int tempFirstIndex, tempSecondIndex;
		int tempNumCopied;
		for (int i = 0; i < length; i++) {
			System.out.print(data[i]);
		} // Of for i
		System.out.println();

		DataNode[][] tempMatrix = new DataNode[2][length];

		// Step 2. Copy data.
		for (int i = 0; i < length; i++) {
			tempMatrix[0][i] = data[i];
		} // Of for i

		// Step 3. Merge. log n rounds
		tempRow = -1;
		for (int tempSize = 1; tempSize <= length; tempSize *= 2) {
			// Reuse the space of the two rows.
			tempRow++;
			System.out.println("Current row = " + tempRow);
			tempActualRow = tempRow % 2;
			tempNextRow = (tempRow + 1) % 2;

			tempGroups = length / (tempSize * 2);
			if (length % (tempSize * 2) != 0) {
				tempGroups++;
			} // Of if
			System.out.println("tempSize = " + tempSize + ", numGroups = " + tempGroups);

			for (tempGroupNumber = 0; tempGroupNumber < tempGroups; tempGroupNumber++) {
				tempFirstStart = tempGroupNumber * tempSize * 2;
				tempSecondStart = tempGroupNumber * tempSize * 2 + tempSize;
				if (tempSecondStart > length - 1) {
					// Copy the first part.
					for (int i = tempFirstStart; i < length; i++) {
						tempMatrix[tempNextRow][i] = tempMatrix[tempActualRow][i];
					} // Of for i
					continue;
				} // Of if
				tempSecondEnd = tempGroupNumber * tempSize * 2 + tempSize * 2 - 1;
				if (tempSecondEnd > length - 1) {
					tempSecondEnd = length - 1;
				} // Of if

				System.out
						.println("Trying to merge [" + tempFirstStart + ", " + (tempSecondStart - 1)
								+ "] with [" + tempSecondStart + ", " + tempSecondEnd + "]");

				tempFirstIndex = tempFirstStart;
				tempSecondIndex = tempSecondStart;
				tempNumCopied = 0;
				while ((tempFirstIndex <= tempSecondStart - 1)
						&& (tempSecondIndex <= tempSecondEnd)) {
					if (tempMatrix[tempActualRow][tempFirstIndex].key <= tempMatrix[tempActualRow][tempSecondIndex].key) {

						tempMatrix[tempNextRow][tempFirstStart
								+ tempNumCopied] = tempMatrix[tempActualRow][tempFirstIndex];
						tempFirstIndex++;
						System.out.println("copying " + tempMatrix[tempActualRow][tempFirstIndex]);
					} else {
						tempMatrix[tempNextRow][tempFirstStart
								+ tempNumCopied] = tempMatrix[tempActualRow][tempSecondIndex];
						System.out.println("copying " + tempMatrix[tempActualRow][tempSecondIndex]);
						tempSecondIndex++;
					} // Of if
					tempNumCopied++;
				} // Of while

				while (tempFirstIndex <= tempSecondStart - 1) {
					tempMatrix[tempNextRow][tempFirstStart
							+ tempNumCopied] = tempMatrix[tempActualRow][tempFirstIndex];
					tempFirstIndex++;
					tempNumCopied++;
				} // Of while

				while (tempSecondIndex <= tempSecondEnd) {
					tempMatrix[tempNextRow][tempFirstStart
							+ tempNumCopied] = tempMatrix[tempActualRow][tempSecondIndex];
					tempSecondIndex++;
					tempNumCopied++;
				} // Of while
			} // Of for groupNumber

			System.out.println("Round " + tempRow);
			for (int i = 0; i < length; i++) {
				System.out.print(tempMatrix[tempNextRow][i] + " ");
			} // Of for j
			System.out.println();
		} // Of for tempStepSize

		data = tempMatrix[tempNextRow];
	}// Of mergeSort

	/**
	 *********************
	 * Test the method.
	 *********************
	 */
	public static void mergeSortTest() {
		int[] tempUnsortedKeys = { 5, 3, 6, 10, 7, 1, 9 };
		String[] tempContents = { "if", "then", "else", "switch", "case", "for", "while" };
		DataArray tempDataArray = new DataArray(tempUnsortedKeys, tempContents);

		System.out.println(tempDataArray);

		tempDataArray.mergeSort();
		System.out.println(tempDataArray);
	}// Of mergeSortTest

第 50 天: 小结

  1. 比较分析各种查找算法.
  2. 设计一个自己的 Hash 函数和一个冲突解决机制.
  3. 比较分析各种排序算法.
  4. 描述各种排序算法的特点和基本思想.
  • 7
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值