一、代码模板
1、递归
// Java
public void recur(int level, int param) {
// terminator
if (level > MAX_LEVEL) {
// process result
return;
}
// process current logic
process(level, param);
// drill down
recur( level: level + 1, newParam);
// restore current status
2、分治
private static int divide_conquer(Problem problem) {
// terminator
if (problem == NULL) {
int res = process_last_result();
return res;
}
// process current logic:split the big problems
subProblems = split_problem(problem)
// drill down:conquer subproblems, merge subresults
res0 = divide_conquer(subProblems[0])
res1 = divide_conquer(subProblems[1])
result = process_result(res0, res1);
// revert the current level states
return result;
}
3、BFS
public class TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int x) {
val = x;
}
}
public List<List<Integer>> levelOrder(TreeNode root) {
List<List<Integer>> allResults = new ArrayList<>();
if (root == null) return allResults;
Queue<TreeNode> nodes = new LinkedList<>();
nodes.add(root);
while (!nodes.isEmpty()) {
int levelSize = nodes.size();
List<Integer> results = new ArrayList<>();
for (int i = 0; i < levelSize; i++) {
TreeNode currNode = nodes.poll();
results.add(currNode.val);
if (currNode.left != null) nodes.add(currNode.left);
if (currNode.right != null) nodes.add(currNode.right);
}
allResults.add(results);
}
return allResults;
}
More:双向BFS
……
4、DFS
4.1 递归
DFS模板:
voidDFS ( Vertex V )
{
visited[V] = true;
for( V 的每个邻接点W )
if( !visited[W] )
DFS( W );
}
public List<List<Integer>> levelOrder(TreeNode root) {
if(root==null) return allResults;
List<List<Integer>> allResults = new ArrayList<>();
travel(root, 0, allResults);
return allResults;
}
private void travel(TreeNode root, int level, List<List<Integer>> results){
// process current node here.
if(results.size()==level) results.add(new ArrayList<>());
results.get(level).add(root.val);
if(root.left!=null) travel(root.left, level+1, results);
if(root.right!=null) travel(root.right, level+1, results);
}
4.2 迭代(非递归写法)
void dfs(TreeNode root) {
if(root!=null) return ;
Set<Integer> visited = new HashSet<>();
stack<TreeNode> stackNode;
stackNode.push(root);
while (!stackNode.isEmpty()) {
TreeNode node = stackNode.pop();
if(visited.contains(node.val)) continue; // already visited
visited.add(node.val);
for (int i = node.children.length() - 1; i >= 0; --i) {
stackNode.push(node.children[i]);
}
}
return ;
}
5、二分
// java
public int binarySearch(int[] array, int target) {
int left = 0, right = array.length - 1, mid;
while (left <= right) {
mid = (right - left) / 2 + left;
if (array[mid] == target) {
return mid;
} else if (array[mid] > target) {
right = mid - 1;
} else {
left = mid + 1;
}
}
return -1;
}
6、二叉树
层序遍历模板可参考上面的BFS。
7、并查集
class UnionFind {
private int count = 0;
private int[] father;
public UnionFind(int n) {
count = n;
father = new int[n];
for (int i = 0; i < n; i++) {
father[i] = i;
}
}
public int find(int p) {
while (p != father[p]) {
father[p] = father[father[p]];
p = father[p];
}
return p;
}
public void union(int p, int q) {
int rootP = find(p);
int rootQ = find(q);
if (rootP != rootQ) {
father[rootP] = rootQ;
count--;
}
}
}
More
// find() 第二个版本,合并的较为彻底
private int find(int p) {
int root = p;
while (root != father[p]) {
root = father[p];
}
while (p != father[p]) {
int tmp = father[p];
father[p] = root;
p = tmp;
}
return root;
}
// find() 第三个版本:递归
public int find (int p) {
if (father[p] == p) {
return p;
}
father[p] = find(father[p]);
return father[p];
}
public boolean connected(int p, int q) {
return find(p)==find(q);
}
// union() 版本2:细化+优化
public UnionFind(int n) {
count = n;
father = new int[n];
rank = new int[n];
for (int i = 0; i < n; i++) {
father[i] = i;
rank[i] = 0;
}
}
public Union(int p, int q) {
int rootP = find(p);
int rootQ = find(q);
if (rootP == rootQ) return;
if (rank[rootP]<rank[rootQ]) father[rootP] = rootQ;
else if (rank[rootP]>rank[rootQ]) father[rootQ] = rootP;
else {
father[rootP] = rootQ; rank[rootQ]++; }
count--;
}
8、排序
1、快排
public static void quickSort(int[] array, int begin, int end) {
if (end <= begin) return;
int pivot = partition(array, begin, end);
quickSort(array, begin, pivot - 1);
quickSort(array, pivot + 1, end);
}
static int partition(int[] a, int begin, int end) {
// pivot: 标杆位置,counter: 小于pivot的元素的个数
int pivot = end, counter = begin;
for (int i = begin; i < end; i++) {
if (a[i] < a[pivot]) {
int temp = a[counter]; a[counter] = a[i]; a[i] = temp;
counter++;
}
}
int temp = a[pivot]; a[pivot] = a[counter]; a[counter] = temp;
return counter;
}
2、归并
public static void mergeSort(int[] array, int left, int right) {
if (right <= left) return;
if mid = (left + right) >> 1; // (left+right)/2
mergeSort(array, left, mid);
mergeSort(array, mid+1, right);
merge(array, left, mid, right);
}
public static void merge(int[] arr, int left, int mid, int right) {
int[] temp = new int[right-left+1]; // 中间数组
int i = left, j = mid+1, k = 0;
while (i<=mid && j<=right) {
temp[k++] = arr[i]<=arr[j] ? arr[i++] : arr[j++];
}
while (i<=mid) temp[k++] = arr[i++];
while (j<=right) temp[k++] = arr[j++];
for (int p=0; p<temp.length; p++) {
arr[left+p] = temp[p];
}
// 也可以用 System.arraycopy(a, start1, b, start2, length)
}
3、堆排序
版本1–PriorityQueue():
void heapSort(int[] arr) {
int len = arr.length;
PriorityQueue<Integer> q = new PriorityQueue<>();
for (int i=0; i<len; i++) {
q.add(a[i]);
}
for (int i=0; i<len; i++) {
a[i] = q.pop();
}
}
版本2–手动实现:
static void heapify(int[] array, int length, int i) {
int left = 2*i+1, right=2*i+2;
int largest = i;
if (left<length && array[left]>array[largest]) {
largest = leftChild;
}
if (right<length && array[right]>array[largest]) {
largest = right;
}
if (largest != i) {
int temp = array; array[i] = array[largest]; array[largest] = temp;
heapify[array, length, largest);
}
}
public static void heapSort(int[] array) {
if (array.length == 0) return;
int length = array.length;
for (int i = length/2-1; i>=0; i--) {
heapify(array, length, i);
}
for (int i=length-1; i>=0; i--) {
int temp = array[0]; array[0] = array[i]; array = temp;
heapify(array, i, 0);
}
}
9、动态规划
二、刷题方法
三、参考
1、递归代码模板
2、分治代码模板
3、BFS 代码模板
4、DFS 代码模板(递归写法、非递归写法)
5、二分查找代码模板