From e48716c883193b2b4be29a906b0cd11fef951bf6 Mon Sep 17 00:00:00 2001 From: krahets Date: Sun, 10 Sep 2023 18:37:26 +0800 Subject: [PATCH] build --- .../iteration_and_recursion.md | 85 +++++++++++++++++-- chapter_greedy/greedy_algorithm.md | 19 ++++- chapter_hashing/hash_algorithm.md | 45 ++++++++-- chapter_heap/build_heap.md | 2 +- chapter_searching/binary_search_edge.md | 26 +++++- chapter_searching/binary_search_insertion.md | 34 +++++++- 6 files changed, 192 insertions(+), 19 deletions(-) diff --git a/chapter_computational_complexity/iteration_and_recursion.md b/chapter_computational_complexity/iteration_and_recursion.md index 40b922eb8..3c55abdc8 100644 --- a/chapter_computational_complexity/iteration_and_recursion.md +++ b/chapter_computational_complexity/iteration_and_recursion.md @@ -158,7 +158,15 @@ status: new === "C" ```c title="iteration.c" - [class]{}-[func]{forLoop} + /* for 循环 */ + int forLoop(int n) { + int res = 0; + // 循环求和 1, 2, ..., n-1, n + for (int i = 1; i <= n; ++i) { + res += i; + } + return res; + } ``` === "Zig" @@ -344,7 +352,17 @@ status: new === "C" ```c title="iteration.c" - [class]{}-[func]{whileLoop} + /* while 循环 */ + int whileLoop(int n) { + int res = 0; + int i = 1; // 初始化条件变量 + // 循环求和 1, 2, ..., n-1, n + while (i <= n) { + res += i; + i++; // 更新条件变量 + } + return res; + } ``` === "Zig" @@ -539,7 +557,19 @@ status: new === "C" ```c title="iteration.c" - [class]{}-[func]{whileLoopII} + /* while 循环(两次更新) */ + int whileLoopII(int n) { + int res = 0; + int i = 1; // 初始化条件变量 + // 循环求和 1, 4, ... + while (i <= n) { + res += i; + // 更新条件变量 + i++; + i *= 2; + } + return res; + } ``` === "Zig" @@ -724,7 +754,23 @@ status: new === "C" ```c title="iteration.c" - [class]{}-[func]{nestedForLoop} + /* 双层 for 循环 */ + char *nestedForLoop(int n) { + // n * n 为对应点数量,"(i, j), " 对应字符串长最大为 6+10*2,加上最后一个空字符 \0 的额外空间 + int size = n * n * 26 + 1; + char *res = malloc(size * sizeof(char)); + + // 循环 i = 1, 2, ..., n-1, n + for (int i = 1; i <= n; ++i) { + // 循环 j = 1, 2, ..., n-1, n + for (int j = 1; j <= n; ++j) { + char tmp[26]; + snprintf(tmp, sizeof(tmp), "(%d, %d), ", i, j); + strncat(res, tmp, size - strlen(res) - 1); + } + } + return res; + } ``` === "Zig" @@ -910,7 +956,16 @@ status: new === "C" ```c title="recursion.c" - [class]{}-[func]{recur} + /* 递归 */ + int recur(int n) { + // 终止条件 + if (n == 1) + return 1; + // 递:递归调用 + int res = recur(n - 1); + // 归:返回结果 + return n + res; + } ``` === "Zig" @@ -1091,7 +1146,14 @@ status: new === "C" ```c title="recursion.c" - [class]{}-[func]{tailRecur} + /* 尾递归 */ + int tailRecur(int n, int res) { + // 终止条件 + if (n == 0) + return res; + // 尾递归调用 + return tailRecur(n - 1, res + n); + } ``` === "Zig" @@ -1278,7 +1340,16 @@ status: new === "C" ```c title="recursion.c" - [class]{}-[func]{fib} + /* 斐波那契数列:递归 */ + int fib(int n) { + // 终止条件 f(1) = 0, f(2) = 1 + if (n == 1 || n == 2) + return n - 1; + // 递归调用 f(n) = f(n-1) + f(n-2) + int res = fib(n - 1) + fib(n - 2); + // 返回结果 f(n) + return res; + } ``` === "Zig" diff --git a/chapter_greedy/greedy_algorithm.md b/chapter_greedy/greedy_algorithm.md index 38878f9d6..8d39366b6 100644 --- a/chapter_greedy/greedy_algorithm.md +++ b/chapter_greedy/greedy_algorithm.md @@ -264,7 +264,24 @@ status: new === "C" ```c title="coin_change_greedy.c" - [class]{}-[func]{coinChangeGreedy} + /* 零钱兑换:贪心 */ + int coinChangeGreedy(int* coins, int size, int amt) { + // 假设 coins 列表有序 + int i = size - 1; + int count = 0; + // 循环进行贪心选择,直到无剩余金额 + while (amt > 0) { + // 找到小于且最接近剩余金额的硬币 + while (i > 0 && coins[i] > amt) { + i--; + } + // 选择 coins[i] + amt -= coins[i]; + count++; + } + // 若未找到可行方案,则返回 -1 + return amt == 0 ? count : -1; + } ``` === "Zig" diff --git a/chapter_hashing/hash_algorithm.md b/chapter_hashing/hash_algorithm.md index b57a25999..007d1de06 100644 --- a/chapter_hashing/hash_algorithm.md +++ b/chapter_hashing/hash_algorithm.md @@ -115,7 +115,6 @@ index = hash(key) % capacity int hash = 0; const int MODULUS = 1000000007; for (unsigned char c : key) { - cout << (int)c << endl; hash ^= (int)c; } return hash & MODULUS; @@ -511,13 +510,47 @@ index = hash(key) % capacity === "C" ```c title="simple_hash.c" - [class]{}-[func]{addHash} + /* 加法哈希 */ + int addHash(char *key) { + long long hash = 0; + const int MODULUS = 1000000007; + for (int i = 0; i < strlen(key); i++) { + hash = (hash + (unsigned char)key[i]) % MODULUS; + } + return (int)hash; + } - [class]{}-[func]{mulHash} + /* 乘法哈希 */ + int mulHash(char *key) { + long long hash = 0; + const int MODULUS = 1000000007; + for (int i = 0; i < strlen(key); i++) { + hash = (31 * hash + (unsigned char)key[i]) % MODULUS; + } + return (int)hash; + } - [class]{}-[func]{xorHash} + /* 异或哈希 */ + int xorHash(char *key) { + int hash = 0; + const int MODULUS = 1000000007; - [class]{}-[func]{rotHash} + for (int i = 0; i < strlen(key); i++) { + hash ^= (unsigned char)key[i]; + } + return hash & MODULUS; + } + + /* 旋转哈希 */ + int rotHash(char *key) { + long long hash = 0; + const int MODULUS = 1000000007; + for (int i = 0; i < strlen(key); i++) { + hash = ((hash << 4) ^ (hash >> 28) ^ (unsigned char)key[i]) % MODULUS; + } + + return (int)hash; + } ``` === "Zig" @@ -789,7 +822,7 @@ $$ === "C" ```c title="built_in_hash.c" - + // C 未提供内置 hash code 函数 ``` === "Zig" diff --git a/chapter_heap/build_heap.md b/chapter_heap/build_heap.md index 9f5004fa6..f688a1198 100644 --- a/chapter_heap/build_heap.md +++ b/chapter_heap/build_heap.md @@ -176,7 +176,7 @@ comments: true maxHeap *h = (maxHeap *)malloc(sizeof(maxHeap)); h->size = size; memcpy(h->data, nums, size * sizeof(int)); - for (int i = parent(size - 1); i >= 0; i--) { + for (int i = parent(h, size - 1); i >= 0; i--) { // 堆化除叶节点以外的其他所有节点 siftDown(h, i); } diff --git a/chapter_searching/binary_search_edge.md b/chapter_searching/binary_search_edge.md index ad5d3665f..edc0587bb 100644 --- a/chapter_searching/binary_search_edge.md +++ b/chapter_searching/binary_search_edge.md @@ -181,7 +181,17 @@ status: new === "C" ```c title="binary_search_edge.c" - [class]{}-[func]{binarySearchLeftEdge} + /* 二分查找最左一个 target */ + int binarySearchLeftEdge(int *nums, int numSize, int target) { + // 等价于查找 target 的插入点 + int i = binarySearchInsertion(nums, numSize, target); + // 未找到 target ,返回 -1 + if (i == numSize || nums[i] != target) { + return -1; + } + // 找到 target ,返回索引 i + return i; + } ``` === "Zig" @@ -389,7 +399,19 @@ status: new === "C" ```c title="binary_search_edge.c" - [class]{}-[func]{binarySearchRightEdge} + /* 二分查找最右一个 target */ + int binarySearchRightEdge(int *nums, int numSize, int target) { + // 转化为查找最左一个 target + 1 + int i = binarySearchInsertion(nums, numSize, target + 1); + // j 指向最右一个 target ,i 指向首个大于 target 的元素 + int j = i - 1; + // 未找到 target ,返回 -1 + if (j == -1 || nums[j] != target) { + return -1; + } + // 找到 target ,返回索引 j + return j; + } ``` === "Zig" diff --git a/chapter_searching/binary_search_insertion.md b/chapter_searching/binary_search_insertion.md index a13900787..b7b86a295 100644 --- a/chapter_searching/binary_search_insertion.md +++ b/chapter_searching/binary_search_insertion.md @@ -249,7 +249,22 @@ status: new === "C" ```c title="binary_search_insertion.c" - [class]{}-[func]{binarySearchInsertionSimple} + /* 二分查找插入点(无重复元素) */ + int binarySearchInsertionSimple(int *nums, int numSize, int target) { + int i = 0, j = numSize - 1; // 初始化双闭区间 [0, n-1] + while (i <= j) { + int m = i + (j - i) / 2; // 计算中点索引 m + if (nums[m] < target) { + i = m + 1; // target 在区间 [m+1, j] 中 + } else if (nums[m] > target) { + j = m - 1; // target 在区间 [i, m-1] 中 + } else { + return m; // 找到 target ,返回插入点 m + } + } + // 未找到 target ,返回插入点 i + return i; + } ``` === "Zig" @@ -531,7 +546,22 @@ status: new === "C" ```c title="binary_search_insertion.c" - [class]{}-[func]{binarySearchInsertion} + /* 二分查找插入点(存在重复元素) */ + int binarySearchInsertion(int *nums, int numSize, int target) { + int i = 0, j = numSize - 1; // 初始化双闭区间 [0, n-1] + while (i <= j) { + int m = i + (j - i) / 2; // 计算中点索引 m + if (nums[m] < target) { + i = m + 1; // target 在区间 [m+1, j] 中 + } else if (nums[m] > target) { + j = m - 1; // target 在区间 [i, m-1] 中 + } else { + j = m - 1; // 首个小于 target 的元素在区间 [i, m-1] 中 + } + } + // 返回插入点 i + return i; + } ``` === "Zig"