Loading docs/ds/stl/priority_queue.md +6 −3 Original line number Diff line number Diff line ```cpp #include <queue> // std::priority_queue // using namespace std; 为了方便区别于 pb_ds 库,不推荐直接使用 using namespace std; // 本文里的所有优先队列都会加上命名空间 // 如果不想加命名空间,需要使用:using std::priority_queue; // 不推荐直接使用 using namespace std; std::priority_queue<T, Container, Compare> /* * T: 储存的元素类型 Loading @@ -15,8 +16,10 @@ std::priority_queue<T, Container, Compare> */ // 构造方式 : std::priority_queue<int>; std::priority_queue<int, vector<int>> // C++11前,请使用 vector<int> >,空格不可省略 std::priority_queue<int, deque<int>, greater<int>> //注意:不可跳过容器参数直接传入比较类 std::priority_queue<int, vector<int>> // C++11前,请使用 vector<int> >,空格不可省略 std::priority_queue<int, deque<int>, greater<int>> // 注意:不可跳过容器参数直接传入比较类 ``` ## 成员函数 : Loading docs/math/prime.md +59 −6 Original line number Diff line number Diff line Loading @@ -34,14 +34,18 @@ bool isPrime(a) { } ``` ### Miller-Rabbin ### Miller-Rabin 素性测试 Miller-Rabbin 算法是进阶的素数判定方法,具有比暴力做法更好的时间复杂度。但是代码复杂度较高,在比赛中使用较少。 Miller-Rabin 素性测试(Miller–Rabin primality test)是进阶的素数判定方法,具有比暴力做法更好的时间复杂度。但是代码复杂度较高,在比赛中使用较少。 它的基本思想是不断地选取不超过 $n-1$ 的基 $b$,并检验是否每次都有 $b^{n-1} \equiv 1 \pmod n$ #### Fermat 素性测试 我们可以根据 [费马小定理](/math/fermat/#_1) 得出一种检验素数的思路: 它的基本思想是不断地选取在 $[2, n-1]$ 中的基 $a$,并检验是否每次都有 $a^{n-1} \equiv 1 \pmod n$ ```c++ bool millerRabbin(int n) { bool millerRabin(int n) { for (int i = 1; i <= s; ++i) { int a = rand() % (n - 2) + 2; if (quickPow(a, n - 1, n) != 1) return 0; Loading @@ -50,6 +54,55 @@ bool millerRabbin(int n) { } ``` 很遗憾,费马小定理的逆定理并不成立,换言之,满足了 $a^{n-1} \equiv 1 \pmod n$ ,$n$ 也不一定是素数。 #### 卡迈克尔数 上面的做法中随机地选择 $a$,很大程度地降低了犯错的概率。但是仍有一类数,上面的做法并不能准确地判断。 对于合数 $n$,如果对于所有正整数 $a$,$a$ 和 $n$ 互素,都有同余式 $a^{n-1} \equiv 1 \pmod n$ 成立,则合数 $n$ 为卡迈克尔数(Carmichael Number),又称为费马伪素数。 比如,$341 = 11 \times 31$ 就是一个卡迈克尔数。 而且我们知道,若 $n$ 为卡迈克尔数,则 $m=2^{n}-1$ 也是一个卡迈克尔数,从而卡迈克尔数的个数是无穷的。 #### 二次探测定理 如果 $p$ 是奇素数,则 $x^2 \equiv 1 \bmod p$ 的解为 $x = 1$ 或者 $x = p - 1 (\bmod p)$; ### 实现 根据卡迈克尔数的性质,可知其一定不是 $p^e$。 不妨将费马小定理和二次探测定理结合起来使用: 将 $n−1$ 分解为 $n−1=u \times 2^t$,不断地对 $u$ 进行平方操作,若发现非平凡平方根时即可判断出其不是素数。 比较正确的 Miller Rabin:(来自 fjzzq2002) ```c++ bool millerRabbin(int n) { int a=n-1,b=0; while(a%2==0) a/=2,++b; for (int i=1,j;i<=s;++i) { int x=rand()%(n-2)+2,v=quickPow(x,a,n); if(v==1||v==n-1) continue; for(j=0;j<b;++j) { v=(long long)v*v%n; if(v==n-1) break; } if(j>=b) return 0; } return 1; } ``` ### 参考 http://www.matrix67.com/blog/archives/234 https://blog.bill.moe/miller-rabin-notes/ ## 反素数 ### 定义 Loading Loading @@ -111,7 +164,7 @@ bool millerRabbin(int n) { ### 常见题型 #### 给定因子数,求满足因子数恰好等于这个数的最小数 #### 求因子数一定的最小数 题目链接:http://codeforces.com/problemset/problem/27/E Loading Loading @@ -153,7 +206,7 @@ int main(){ } ``` #### 给定一个 n,求 n 以内因子数最多的数 #### 求 n 以内因子数最多的数 http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=1562 Loading mkdocs.yml +1 −0 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ nav: - 进制相关: math/base.md - 素数: math/prime.md - 最大公约数: math/gcd.md - 贝祖定理: math/bezouts.md - 欧拉函数: math/euler.md - 筛法: math/sieve.md - 莫比乌斯反演: math/mobius.md Loading Loading
docs/ds/stl/priority_queue.md +6 −3 Original line number Diff line number Diff line ```cpp #include <queue> // std::priority_queue // using namespace std; 为了方便区别于 pb_ds 库,不推荐直接使用 using namespace std; // 本文里的所有优先队列都会加上命名空间 // 如果不想加命名空间,需要使用:using std::priority_queue; // 不推荐直接使用 using namespace std; std::priority_queue<T, Container, Compare> /* * T: 储存的元素类型 Loading @@ -15,8 +16,10 @@ std::priority_queue<T, Container, Compare> */ // 构造方式 : std::priority_queue<int>; std::priority_queue<int, vector<int>> // C++11前,请使用 vector<int> >,空格不可省略 std::priority_queue<int, deque<int>, greater<int>> //注意:不可跳过容器参数直接传入比较类 std::priority_queue<int, vector<int>> // C++11前,请使用 vector<int> >,空格不可省略 std::priority_queue<int, deque<int>, greater<int>> // 注意:不可跳过容器参数直接传入比较类 ``` ## 成员函数 : Loading
docs/math/prime.md +59 −6 Original line number Diff line number Diff line Loading @@ -34,14 +34,18 @@ bool isPrime(a) { } ``` ### Miller-Rabbin ### Miller-Rabin 素性测试 Miller-Rabbin 算法是进阶的素数判定方法,具有比暴力做法更好的时间复杂度。但是代码复杂度较高,在比赛中使用较少。 Miller-Rabin 素性测试(Miller–Rabin primality test)是进阶的素数判定方法,具有比暴力做法更好的时间复杂度。但是代码复杂度较高,在比赛中使用较少。 它的基本思想是不断地选取不超过 $n-1$ 的基 $b$,并检验是否每次都有 $b^{n-1} \equiv 1 \pmod n$ #### Fermat 素性测试 我们可以根据 [费马小定理](/math/fermat/#_1) 得出一种检验素数的思路: 它的基本思想是不断地选取在 $[2, n-1]$ 中的基 $a$,并检验是否每次都有 $a^{n-1} \equiv 1 \pmod n$ ```c++ bool millerRabbin(int n) { bool millerRabin(int n) { for (int i = 1; i <= s; ++i) { int a = rand() % (n - 2) + 2; if (quickPow(a, n - 1, n) != 1) return 0; Loading @@ -50,6 +54,55 @@ bool millerRabbin(int n) { } ``` 很遗憾,费马小定理的逆定理并不成立,换言之,满足了 $a^{n-1} \equiv 1 \pmod n$ ,$n$ 也不一定是素数。 #### 卡迈克尔数 上面的做法中随机地选择 $a$,很大程度地降低了犯错的概率。但是仍有一类数,上面的做法并不能准确地判断。 对于合数 $n$,如果对于所有正整数 $a$,$a$ 和 $n$ 互素,都有同余式 $a^{n-1} \equiv 1 \pmod n$ 成立,则合数 $n$ 为卡迈克尔数(Carmichael Number),又称为费马伪素数。 比如,$341 = 11 \times 31$ 就是一个卡迈克尔数。 而且我们知道,若 $n$ 为卡迈克尔数,则 $m=2^{n}-1$ 也是一个卡迈克尔数,从而卡迈克尔数的个数是无穷的。 #### 二次探测定理 如果 $p$ 是奇素数,则 $x^2 \equiv 1 \bmod p$ 的解为 $x = 1$ 或者 $x = p - 1 (\bmod p)$; ### 实现 根据卡迈克尔数的性质,可知其一定不是 $p^e$。 不妨将费马小定理和二次探测定理结合起来使用: 将 $n−1$ 分解为 $n−1=u \times 2^t$,不断地对 $u$ 进行平方操作,若发现非平凡平方根时即可判断出其不是素数。 比较正确的 Miller Rabin:(来自 fjzzq2002) ```c++ bool millerRabbin(int n) { int a=n-1,b=0; while(a%2==0) a/=2,++b; for (int i=1,j;i<=s;++i) { int x=rand()%(n-2)+2,v=quickPow(x,a,n); if(v==1||v==n-1) continue; for(j=0;j<b;++j) { v=(long long)v*v%n; if(v==n-1) break; } if(j>=b) return 0; } return 1; } ``` ### 参考 http://www.matrix67.com/blog/archives/234 https://blog.bill.moe/miller-rabin-notes/ ## 反素数 ### 定义 Loading Loading @@ -111,7 +164,7 @@ bool millerRabbin(int n) { ### 常见题型 #### 给定因子数,求满足因子数恰好等于这个数的最小数 #### 求因子数一定的最小数 题目链接:http://codeforces.com/problemset/problem/27/E Loading Loading @@ -153,7 +206,7 @@ int main(){ } ``` #### 给定一个 n,求 n 以内因子数最多的数 #### 求 n 以内因子数最多的数 http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=1562 Loading
mkdocs.yml +1 −0 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ nav: - 进制相关: math/base.md - 素数: math/prime.md - 最大公约数: math/gcd.md - 贝祖定理: math/bezouts.md - 欧拉函数: math/euler.md - 筛法: math/sieve.md - 莫比乌斯反演: math/mobius.md Loading