关于正多边形的尺规作图

· · 个人记录

由于 Gauss 的工作,所以我们只需要讨论如下几种正多边形:

  1. 正三边形
  2. 正五边形
  3. 正十七边形
  4. 正二百五十七边形
  5. 正六万五千五百三十七边形

正三边形、正五边形的尺规作图请到课本里找。

正十七边形

我们需要求出单位根 \omega_{17}^1 即可。

\alpha_0=\sum_{i=0}^{7}\omega_{17}^{3^{2i}}=\omega_{17}^1+\omega_{17}^9+\omega_{17}^{13}+\omega_{17}^{15}+\omega_{17}^{16}+\omega_{17}^8+\omega_{17}^4+\omega_{17}^2 \alpha_1=\sum_{i=0}^{7}\omega_{17}^{3^{2i+1}}=\omega_{17}^3+\omega_{17}^{10}+\omega_{17}^5+\omega_{17}^{11}+\omega_{17}^{14}+\omega_{17}^7+\omega_{17}^{12}+\omega_{17}^6

其中 \omega 为单位根。

显然易得:

\begin{cases}\alpha_0+\alpha_1&=-1\\\alpha_0\alpha_1&=-4\end{cases}

什么?你说这不显然?

行,满足你:

\begin{aligned}\alpha_0+\alpha_1&=\omega_{17}^1+\omega_{17}^9+\omega_{17}^{13}+\omega_{17}^{15}+\omega_{17}^{16}+\omega_{17}^8+\omega_{17}^4+\omega_{17}^2+\omega_{17}^1+\omega_{17}^9+\omega_{17}^{13}+\omega_{17}^{15}+\omega_{17}^{16}+\omega_{17}^8+\omega_{17}^4+\omega_{17}^2\\&=\sum_{i=1}^{16}\omega_{17}^i\\&=-1\end{aligned} \begin{aligned}\alpha_0\alpha_1&=\omega_{17}^4+\omega_{17}^{11}+\omega_{17}^6+\omega_{17}^{12}+\omega_{17}^{15}+\omega_{17}^8+\omega_{17}^{13}+\omega_{17}^7+\omega_{17}^{12}+\omega_{17}^2+\omega_{17}^{14}+\omega_{17}^3+\omega_{17}^6+\omega_{17}^{16}+\omega_{17}^4+\omega_{17}^{15}+\omega_{17}^{16}+\omega_{17}^6+\omega_{17}^1+\omega_{17}^7+\omega_{17}^{10}+\omega_{17}^3+\omega_{17}^8+\omega_{17}^2+\omega_{17}^1+\omega_{17}^8+\omega_{17}^3+\omega_{17}^9+\omega_{17}^{12}+\omega_{17}^5+\omega_{17}^{10}+\omega_{17}^4+\omega_{17}^2+\omega_{17}^9+\omega_{17}^4+\omega_{17}^{10}+\omega_{17}^{13}+\omega_{17}^6+\omega_{17}^{11}+\omega_{17}^5+\omega_{17}^{11}+\omega_{17}^1+\omega_{17}^{13}+\omega_{17}^2+\omega_{17}^5+\omega_{17}^{15}+\omega_{17}^3+\omega_{17}^{14}+\omega_{17}^7+\omega_{17}^{14}+\omega_{17}^9+\omega_{17}^{15}+\omega_{17}^1+\omega_{17}^{11}+\omega_{17}^{16}+\omega_{17}^{10}+\omega_{17}^5+\omega_{17}^{12}+\omega_{17}^7+\omega_{17}^{13}+\omega_{17}^{16}+\omega_{17}^9+\omega_{17}^{14}+\omega_{17}^8\\&=4\omega_{17}^1+4\omega_{17}^2+4\omega_{17}^3+4\omega_{17}^4+4\omega_{17}^5+4\omega_{17}^6+4\omega_{17}^7+4\omega_{17}^8+4\omega_{17}^9+4\omega_{17}^{10}+4\omega_{17}^{11}+4\omega_{17}^{12}+4\omega_{17}^{13}+4\omega_{17}^{14}+4\omega_{17}^{15}+4\omega_{17}^{16}\\&=4\sum_{i=1}^{16}\omega_{17}^i\\&=-4\end{aligned}

然后就可以解出来:

\alpha_{0,1}=\dfrac{-1\pm\sqrt{17}}2$ 或者 $\alpha_{0,1}=\dfrac{-1\mp\sqrt{17}}2

再通过数值计算,我们可以得出:

\alpha_{0,1}=\dfrac{-1\pm\sqrt{17}}2

接下来,我们令

\beta_i=\sum_{j=0}^3\omega_{17}^{3^{4j+i}}(0\le i<4)

即:

\beta_0=\omega_{17}^1+\omega_{17}^{13}+\omega_{17}^{16}+\omega_{17}^4 \beta_1=\omega_{17}^3+\omega_{17}^5+\omega_{17}^{14}+\omega_{17}^{12} \beta_2=\omega_{17}^9+\omega_{17}^{15}+\omega_{17}^8+\omega_{17}^2 \beta_3=\omega_{17}^{10}+\omega_{17}^{11}+\omega_{17}^7+\omega_{17}^6

那么显然有:

\begin{cases}\beta_0+\beta_2&=\alpha_0\\\beta_0\beta_2&=-1\end{cases} \begin{cases}\beta_1+\beta_3&=\alpha_1\\\beta_1\beta_3&=-1\end{cases}

证明:

\beta_0+\beta_2=\omega_{17}^1+\omega_{17}^{13}+\omega_{17}^{16}+\omega_{17}^4+\omega_{17}^9+\omega_{17}^{15}+\omega_{17}^8+\omega_{17}^2=\alpha_0 \beta_0\beta_2=\omega_{17}^{10}+\omega_{17}^{16}+\omega_{17}^9+\omega_{17}^3+\omega_{17}^5+\omega_{17}^{11}+\omega_{17}^4+\omega_{17}^{15}+\omega_{17}^8+\omega_{17}^{14}+\omega_{17}^7+\omega_{17}^1+\omega_{17}^{13}+\omega_{17}^2+\omega_{17}^{12}+\omega_{17}^6=-1 \beta_1+\beta_3=\omega_{17}^3+\omega_{17}^5+\omega_{17}^{14}+\omega_{17}^{12}+\omega_{17}^{10}+\omega_{17}^{11}+\omega_{17}^7+\omega_{17}^6=\alpha_1 \beta_1\beta_3=\omega_{17}^{13}+\omega_{17}^{14}+\omega_{17}^{10}+\omega_{17}^9+\omega_{17}^{15}+\omega_{17}^{16}+\omega_{17}^{12}+\omega_{17}^{11}+\omega_{17}^7+\omega_{17}^8+\omega_{17}^4+\omega_{17}^3+\omega_{17}^5+\omega_{17}^6+\omega_{17}^2+\omega_{17}^1=-1

然后我们解得:

\begin{cases}\beta_{0,2}&=\dfrac{\alpha_0\pm\sqrt{\alpha_0^2+4}}2\\\beta_{1,3}&=\dfrac{\alpha_1\pm\sqrt{\alpha_1^2+4}}2\end{cases}

然后再根据数值计算,我们可以得到上面的结果是对的。

然后再令:

\gamma_i=\sum_{j=0}^1\omega_{17}^{3^{8j+i}}(0\le i<8)

注意我们这里只需要求出 \gamma_0,\gamma_1 的值即可,原因在下面会解释。

那么我们可以得到:

\begin{cases}\gamma_0+\gamma_1&=\omega_{17}^1+\omega_{17}^{16}+\omega_{17}^{13}+\omega_{17}^4=\beta_0\\\gamma_0\gamma_1&=\omega_{17}^{14}+\omega_{17}^5+\omega_{17}^{12}+\omega_{17}^3=\beta_1\end{cases}

解得:

\gamma_{0,1}=\dfrac{\beta_0\pm\sqrt{\beta_0^2-4\beta_1}}2

然后我们观察 \gamma_0=\omega_{17}^0+\omega_{17}^{16},因为 \omega_{17}^0\omega_{17}^{16} 互为共轭,所以:\gamma_0=2\Re(\omega_{17}^1),再根据 |\omega_{17}^1|=1 就可以求出 \omega_{17}^1 了。

所以,我们来总结一下 \omega_{17}^1 的构造方法,令:

\alpha_0=\dfrac{-1+\sqrt{17}}2 \alpha_1=\dfrac{-1-\sqrt{17}}2 \beta_0=\dfrac{\alpha_0+\sqrt{\alpha_0^2+4}}2 \beta_1=\dfrac{\alpha_1+\sqrt{\alpha_1^2+4}}2 \gamma_0=\dfrac{\beta_0+\sqrt{\beta_0^2-4\beta_1}}2 z=\dfrac{\gamma_0}2

则:

\omega_{17}^1=z+i\sqrt{1-z^2}

如果整合在一起就是这个样子(不想化简了):

z=\dfrac{\dfrac{\dfrac{-1+\sqrt{17}}2+\sqrt{\left(\dfrac{-1+\sqrt{17}}2\right)^2+4}}2+\sqrt{\left(\dfrac{\dfrac{-1+\sqrt{17}}2+\sqrt{\left(\dfrac{-1+\sqrt{17}}2\right)^2+4}}2\right)^2-4\left(\dfrac{\dfrac{-1-\sqrt{17}}2+\sqrt{\left(\dfrac{-1-\sqrt{17}}2\right)^2+4}}2\right)}}4 \omega_{17}^1=z+i\sqrt{1-z^2}

结合数值计算我们可以得到中间表达式的大小关系(由于程序原因,需要倒着看):

\begin{cases}c_0+c_4=b_0\\c_0c_4=b_1\\c_0>c_4\\b_0+b_2=a_0\\b_0b_2=z_0\\b_0>b_2\\b_1+b_3=a_1\\b_1b_3=a_0+a_1\\b_1>b_3\\a_0+a_1=z_0\\a_0a_1=4z_0\\a_0>a_1\\z_0=-1\end{cases}

Carlyle Circle

考虑两个数 s,p,其可以确定一个二次方程 x^2-sx+p=0,在给定 s,p 的情况下,我们可以尺规作图求出其两个根。

那么有没有很简单的方法?有。

我们作两个点 (0,1)(s,p),以其为直径作圆,该圆交于 x 轴于两点,则这两点为 x^2-sx+p 的两个根。

注意以 (s,1)(0,p) 做直径也可以。

证明不会。

这个方法就叫 Carlyle Circle。

正二百五十七边形

同正十七边形一样,我们只需要求出 \omega_{257}^1 即可。

我们设:

\begin{cases}a_j=\sum_{i=0}^{127}\omega_{257}^{3^{2i+j}}&(0\le j<2)\\b_j=\sum_{i=0}^{63}\omega_{257}^{3^{4i+j}}&(0\le j<4)\\c_j=\sum_{i=0}^{31}\omega_{257}^{3^{8i+j}}&(0\le j<8)\\d_j=\sum_{i=0}^{15}\omega_{257}^{3^{16i+j}}&(0\le j<16)\\e_j=\sum_{i=0}^7\omega_{257}^{3^{32i+j}}&(0\le j<32)\\f_j=\sum_{i=0}^3\omega_{257}^{3^{64i+j}}&(0\le j<64)\\g_j=\sum_{i=0}^1\omega_{257}^{3^{128i+j}}&(0\le j<128)\end{cases}

我们显然有 \Re(\omega_{257}^1)=\dfrac{g_0}2,所以求出 g_0 即可。

我们考虑 g_{64},通过符号计算我们得到:

\begin{cases}g_0+g_{64}=f_0\\g_0g_{64}=f_{56}\end{cases}

问题转化为计算 f_0,f_{56},同样找两个与其配对的:

\begin{cases}f_0+f_{32}=e_0\\f_0f_{32}=e_1+e_{23}\\f_{24}+f_{56}=e_{24}\\f_{24}f_{56}=e_{15}+e_{25}\end{cases}

问题转化为计算 e_0,e_1,e_{15},e_{23},e_{24},e_{25},再次配对:

\begin{cases}e_0+e_{16}=d_0\\e_0e_{16}=d_0+d_1+d_2+d_5\\e_1+e_{17}=d_1\\e_1e_{17}=d_1+d_2+d_3+d_6\\e_{15}+e_{31}=d_{15}\\e_{15}e_{31}=d_0+d_1+d_4+d_{15}\\e_7+e_{23}=d_7\\e_7e_{23}=d_7+d_8+d_9+d_{12}\\e_8+e_{24}=d_8\\e_8e_{24}=d_8+d_9+d_{10}+d_{13}\\e_9+e_{25}=d_9\\e_9e_{25}=d_9+d_{10}+d_{11}+d_{14}\end{cases}

然后 d_0,d_1,d_2,d_3,d_4,d_5,d_6,d_7,d_8,d_9,d_{10},d_{11},d_{12},d_{13},d_{14},d_{15} 都要计算。

还是配对:

\begin{cases}d_0+d_8=c_0\\d_0d_8=2c_0+2c_2+c_4+2c_5+c_6\\d_1+d_9=c_1\\d_1d_9=2c_1+2c_3+c_5+2c_6+c_7\\d_2+d_{10}=c_2\\d_2d_{10}=c_0+2c_2+2c_4+c_6+2c_7\\d_3+d_{11}=c_3\\d_3d_{11}=2c_0+c_1+2c_3+2c_5+c_7\\d_4+d_{12}=c_4\\d_4d_{12}=c_0+2c_1+c_2+2c_4+2c_6\\d_5+d_{13}=c_5\\d_5d_{13}=c_1+2c_2+c_3+2c_5+2c_7\\d_6+d_{14}=c_6\\d_6d_{14}=2c_0+c_2+2c_3+c_4+2c_6\\d_7+d_{15}=c_7\\d_7d_{15}=2c_1+c_3+2c_4+c_5+2c_7\end{cases}

问题转化为计算 c_0,c_1,c_2,c_3,c_4,c_5,c_6,c_7,还是配对:

\begin{cases}c_0+c_4=b_0\\c_0c_4=2b_0+5b_1+4b_2+5b_3\\c_1+c_5=b_1\\c_1c_5=5b_0+2b_1+5b_2+4b_3\\c_2+c_6=b_2\\c_2c_6=4b_0+5b_1+2b_2+5b_3\\c_3+c_7=b_3\\c_3c_7=5b_0+4b_1+5b_2+2b_3\end{cases}

问题转化为计算 b_0,b_1,b_2,b_3,还是配对:

\begin{cases}b_0+b_2=a_0\\b_0b_2=-16\\b_1+b_3=a_1\\b_1b_3=-16\end{cases}

问题转化为计算 a_0,a_1,列出方程:

\begin{cases}a_0+a_1=-1\\a_0a_1=-64\end{cases}

解出 a_0,a_1 后就可以一路推下去了,最终结果就像这样:

\begin{cases}g_0+g_{64}=f_0\\g_0g_{64}=f_{56}\\g_0>g_{64}\\f_0+f_{32}=e_0\\f_0f_{32}=e_1+e_{23}\\f_0>f_{32}\\f_{24}+f_{56}=e_{24}\\f_{24}f_{56}=e_{15}+e_{25}\\f_{24}<f_{56}\\e_0+e_{16}=d_0\\e_0e_{16}=d_0+d_1+d_2+d_5\\e_0>e_{16}\\e_1+e_{17}=d_1\\e_1e_{17}=d_1+d_2+d_3+d_6\\e_1>e_{17}\\e_7+e_{23}=d_7\\e_7e_{23}=d_7+d_8+d_9+d_{12}\\e_7<e_{23}\\e_8+e_{24}=d_8\\e_8e_{24}=d_8+d_9+d_{10}+d_{13}\\e_8<e_{24}\\e_9+e_{25}=d_9\\e_9e_{25}=d_9+d_{10}+d_{11}+d_{14}\\e_9<e_{25}\\e_{15}+e_{31}=d_{15}\\e_{15}e_{31}=d_0+d_1+d_4+d_{15}\\e_{15}>e_{31}\\d_0+d_8=c_0\\d_0d_8=2c_0+2c_2+c_4+2c_5+c_6\\d_0>d_8\\d_1+d_9=c_1\\d_1d_9=2c_1+2c_3+c_5+2c_6+c_7\\d_1>d_9\\d_2+d_{10}=c_2\\d_2d_{10}=c_0+2c_2+2c_4+c_6+2c_7\\d_2>d_{10}\\d_3+d_{11}=c_3\\d_3d_{11}=2c_0+c_1+2c_3+2c_5+c_7\\d_3>d_{11}\\d_4+d_{12}=c_4\\d_4d_{12}=c_0+2c_1+c_2+2c_4+2c_6\\d_4>d_{12}\\d_5+d_{13}=c_5\\d_5d_{13}=c_1+2c_2+c_3+2c_5+2c_7\\d_5>d_{13}\\d_6+d_{14}=c_6\\d_6d_{14}=2c_0+c_2+2c_3+c_4+2c_6\\d_6<d_{14}\\d_7+d_{15}=c_7\\d_7d_{15}=2c_1+c_3+2c_4+c_5+2c_7\\d_7>d_{15}\\c_0+c_4=b_0\\c_0c_4=2b_0+5b_1+4b_2+5b_3\\c_0>c_4\\c_1+c_5=b_1\\c_1c_5=5b_0+2b_1+5b_2+4b_3\\c_1<c_5\\c_2+c_6=b_2\\c_2c_6=4b_0+5b_1+2b_2+5b_3\\c_2>c_6\\c_3+c_7=b_3\\c_3c_7=5b_0+4b_1+5b_2+2b_3\\c_3<c_7\\b_0+b_2=a_0\\b_0b_2=16a_0+16a_1\\b_0>b_2\\b_1+b_3=a_1\\b_1b_3=16a_0+16a_1\\b_1>b_3\\a_0+a_1=z_0\\a_0a_1=64z_0\\a_0>a_1\\z_0=-1\end{cases}

什么?你要看到所有的圆和直线?

可以看这个。

点的坐标范围大概是 [-30,30]\times[-40,40] 之间,所以大概能画在 A4 纸上。

正六万五千五百三十七边形

还是类似的思路:设

\begin{cases}a_j=\sum_{i=0}^{32767}\omega_{32768}^{3^{2i+j}}&(0\le j<2)\\b_j=\sum_{i=0}^{16383}\omega_{65537}^{3^{4i+j}}&(0\le j<4)\\c_j=\sum_{i=0}^{8191}\omega_{65537}^{3^{8i+j}}&(0\le j<8)\\d_j=\sum_{i=0}^{4095}\omega_{65537}^{3^{16i+j}}&(0\le j<16)\\e_j=\sum_{i=0}^{2047}\omega_{65537}^{3^{32i+j}}&(0\le j<32)\\f_j=\sum_{i=0}^{1023}\omega_{65537}^{3^{64i+j}}&(0\le j<64)\\g_j=\sum_{i=0}^{511}\omega_{65537}^{3^{128i+j}}&(0\le j<128)\\h_j=\sum_{i=0}^{255}\omega_{65537}^{3^{256i+j}}&(0\le j<256)\\k_j=\sum_{i=0}^{127}\omega_{65537}^{3^{512i+j}}&(0\le j<512)\\l_j=\sum_{i=0}^{63}\omega_{65537}^{3^{1024i+j}}&(0\le j<1024)\\o_j=\sum_{i=0}^{31}\omega_{65537}^{3^{2048i+j}}&(0\le j<2048)\\p_j=\sum_{i=0}^{15}\omega_{65537}^{3^{4096i+j}}&(0\le j<4096)\\q_j=\sum_{i=0}^7\omega_{65537}^{3^{8192i+j}}&(0\le j<8192)\\r_j=\sum_{i=0}^3\omega_{65537}^{3^{16384i+j}}&(0\le j<16384)\\s_j=\sum_{i=0}^1\omega_{65537}^{3^{32768i+j}}&(0\le j<32768)\end{cases}

仍然从底层倒着推,我们显然有 \Re(\omega_{65537}^1)=\dfrac{s_1}2,所以求出 s_1 即可。

由于过程太长了,所以请运行以下程序产生:

#include <iostream>
#include <complex>
#include <vector>
using namespace std;
const int m = 4;
const int n = (1 << (1 << m)) + 1;
const double pi = 3.14159265358979323846;
struct Number {
    short x[n]; // 这里 short 足够了,最大值 16384.
    Number() {
        for (int i = 0; i < n; i++) {
            x[i] = 0;
        }
    }
};
Number operator + (const Number & a, const Number & b) {
    Number c;
    for (int i = 0; i < n; i++) {
        c.x[i] = a.x[i] + b.x[i];
    }
    return c;
}
Number operator - (const Number & a, const Number & b) {
    Number c;
    for (int i = 0; i < n; i++) {
        c.x[i] = a.x[i] - b.x[i];
    }
    return c;
}
Number operator * (const Number & a, const Number & b) {
    Number c;
    for (int i = 0; i < n; i++) {
        if (a.x[i] > 0) {
            for (int j = 0; j < n; j++) {
                c.x[(i + j) % n] += a.x[i] * b.x[j];
            }
        }
    }
    return c;
}
Number operator * (const Number & a, const int & b) {
    Number c;
    for (int i = 0; i < n; i++) {
        c.x[i] += a.x[i] * b;
    }
    return c;
}
bool operator == (const Number & a, const Number & b) {
    for (int i = 0; i < n; i++) {
        if (a.x[i] != b.x[i]) {
            return false;
        }
    }
    return true;
}
complex < double > omega(int k) {
    return complex < double > (cos(2 * pi * k / n), sin(2 * pi * k / n));
}
complex < double > calc(Number a) {
    complex < double > x = 0;
    for (int i = 0; i < n; i++) {
        x += complex < double > (a.x[i], 0) * omega(i);
    }
    return x;
}
string to_cof(int x) {
    if (x == 1) {
        return "";
    } else {
        return to_string(x);
    }
}
string warpper(int x) {
    if (x <= 9) {
        return to_string(x);
    } else {
        return "{" + to_string(x) + "}";
    }
}
string term(int x, int y) {
    string res;
    if (x > 0) {
        res = "+";
    }
    res += to_cof(x) + "\\omega_{" + to_string(n) + "}^" + warpper(y);
    return res;
}
void print_LaTeX(Number x) {
    string s;
    for (int i = 0; i < n; i++) {
        if (x.x[i] != 0) {
            s += term(x.x[i], i);
        }
    }
    if (s.length() == 0) {
        cout << 0 << endl;
    } else {
        if (s[0] == '+') {
            s = s.substr(1, s.length() - 1);
        }
        cout << s << endl;
    }
}
void print(Number x) {
    for (int i = 0; i < n; i++) {
        printf("%d ", x.x[i]);
    }
    printf("\n");
}
int pow(int a, int b) {
    int ans = 1;
    while (b != 0) {
        if ((b & 1) == 1) {
            ans = 1ll * ans * a % n;
        }
        a = 1ll * a * a % n;
        b = b / 2;
    }
    return ans;
}
int get_first(Number x) {
    for (int i = 0; i < n; i++) {
        if (x.x[i] != 0) {
            return i;
        }
    }
    return -1;
}
vector < int > get(Number x, const vector < Number > & a) {
    vector < int > res(0, a.size());
    for (int i = 0, first; i < (int)a.size(); i++) {
        first = get_first(a[i]);
        if (first != -1) {
            res.push_back(x.x[first]);
            for (int j = 0; j < n; j++) {
                if (a[i].x[j] != 0) {
                    if (x.x[j] != res[i]) {
                        printf("Error.\n");
                        return vector < int > ();
                    }
                }
            }
            x = x - a[i] * res[i];
        }
    }
    if (x == Number()) {
        return res;
    } else {
        return res;
    }
}
void print(vector < int > vec) {
    for (int x : vec) {
        printf("%d ", x);
    }
    printf("\n");
}
bool vis[n];
void print_LaTeX(vector < int > vec, char name) {
    bool first = true;
    for (int i = 0; i < (int)vec.size(); i++) {
        if (vec[i] > 0) {
            vis[i] = true;
            if (!first) {
                printf("+");
            } else {
                first = false;
            }
            if (vec[i] == 1) {
                printf("%c_", name);
                cout << warpper(i);
            } else {
                printf("%d%c_", vec[i], name);
                cout << warpper(i);
            }
        }
    }
    printf("\\\\");
}
vector < vector < int > > vec;
//int which[n];
void get_which(int i) { // 分成 2 ^ i 个组.
    vec.clear();
    for (int j = 0; j < (1 << i); j++) {
        vec.push_back(vector < int > ());
        for (int k = 0; k < (n - 1) / (1 << i); k++) {
            vec[j].push_back(pow(3, (k << i) + j));
//          which[pow(3, (k << i) + j)] = j;
        }
    }
}
vector < int > get(Number x, int i) {
    vector < int > res((1 << i), 0);
    for (int j = 0; j < (1 << i); j++) {
        res[j] = x.x[vec[j][0]];
        for (int k : vec[j]) {
            if (x.x[k] != res[j]) {
                printf("Error.");
            } else {
                x.x[k] = 0;
            }
        }
    }
    for (int j = 0; j < n; j++) {
        if (x.x[j] != 0) {
            printf("Error.");
        }
    }
    return res;
}
Number get_number(int i, int j) { // 2 ^ i 个中的第 j 个.
    Number x;
    for (int k = 0; k < (n - 1) / (1 << i); k++) {
        x.x[pow(3, (k << i) + j)] = 1;
    }
    return x;
}
const char * name = "zabcdefghklopqrs";
bool todo[n];
int main() {
    freopen("output.txt", "w", stdout);
    // now 表示要运算的数的层数.
    printf("$$\\begin{cases}");
    todo[0] = true;
    for (int now = (1 << m) - 1; now > 0; now--) {
        for (int i = 0; i < n; i++) {
            vis[i] = false;
        }
        int delta = 1 << (now - 1);
        get_which(now - 1);
        for (int x = 0, y; x < delta; x++) {
            if (todo[x]) {
                y = (x + delta) % (1 << now);
                Number a = get_number(now, x) + get_number(now, y);
                cout << string() + name[now] + "_" + warpper(x) + "+" + name[now] + "_" + warpper(y) + "=";
                print_LaTeX(get(a, now - 1), name[now - 1]);
                Number b = get_number(now, x) * get_number(now, y);
                cout << string() + name[now] + "_" + warpper(x) + name[now] + "_" + warpper(y) + "=";
                print_LaTeX(get(b, now - 1), name[now - 1]);
            }
        }
//      printf("\n");
        for (int i = 0; i < delta / 2; i++) {
            if (vis[i] || vis[i + delta / 2]) {
//          printf("todo[%d] = true;\n", i);
                todo[i] = true;
            } else {
                todo[i] = false;
            }
        }
//      for (int i = 0; i < n; i++) {
//          if (vis[i]) {
//              printf("%c_", name[now - 1]);
//              cout << warpper(i) << ',';
//          }
//      }
        fprintf(stderr, "Level %d finished.\n", now);
    }
    printf("z_0=-1\\end{cases}$$");
    return 0;
}
/*
abcdefghklopqrs
123456789012345
a - 1 - 2
b - 2 - 4
c - 3 - 8
d - 4 - 16
e - 5 - 32
f - 6 - 64
g - 7 - 128
h - 8 - 256
k - 9 - 512
l - 10 - 1024
o - 11 - 2048
p - 12 - 4096
q - 13 - 8192
r - 14 - 16384
s - 15 - 32768
*/

看的时候要倒过来,在我的计算机上运行了 70s。

你要知道当时 Hermes 搞了 10 年,我们只花了一分钟多。