題解 Luogu P4240 毒瘤之神的考驗

2022-09-19 13:18:11 字數 4728 閱讀 4220

p4240 毒瘤之神的考驗

引理:\[\varphi(ij) = \dfrac

\]

證明:

\[\begin

\varphi(i) \varphi(j) \gcd(i, j)

& = i \prod_, p_1\mid i} \dfrac \cdot j \prod_, p_2\mid j} \dfrac \cdot \gcd(i, j) \\

& = ij \gcd(i, j) \left(\prod_, p_1\mid i} \dfrac \prod_, p_2\mid j} \dfrac \right)

\end

\]你會發現所有 \(\gcd(i, j)\) 的質因數都被算了 \(2\) 次。

\[\begin

& = \left(ij\prod_, p_1\mid ij} \dfrac \right) \cdot \left(\gcd(i, j) \prod_, p_2\mid \gcd(i, j)} \dfrac \right) \\

& = \varphi(ij) \varphi(\gcd(i, j))

\end

\]把 \(\varphi(\gcd(i, j))\) 除過去即可。

不妨設 \(n\le m\),根據引理,有

\[\begin

ans& = \sum_^n \sum_^m \dfrac \\

& = \sum_^n \sum_^n \sum_^m \dfrac [\gcd(i, j) = d] \\

& = \sum_^n \dfrac \sum_^\right\rfloor} \sum_^\right\rfloor} \varphi(id) \varphi(jd) [\gcd(i, j) = 1] \\

& = \sum_^n \dfrac \sum_^\right\rfloor} \varphi(id) \sum_^\right\rfloor} \varphi(jd) [\gcd(i, j) = 1] \\

& = \sum_^n \dfrac \sum_^\right\rfloor} \varphi(id) \sum_^\right\rfloor} \varphi(jd) \sum_ \mu(k) \\

& = \sum_^n \dfrac \sum_^\right\rfloor} \mu(k) \sum_^\right\rfloor} \varphi(idk) \sum_^\right\rfloor} \varphi(jdk) \\

& = \sum_^n \sum_ \dfrac \mu\left(\dfrac\right) \sum_^\right\rfloor} \varphi(it) \sum_^\right\rfloor} \varphi(jt)

\end

\]其中

\[f(n) = \sum_ \dfrac\right)}

\]不是積性函式(它甚至不一定是整數),直接預處理逆元 \(\theta(n\ln n)\) 計算。

對於\[\sum_^\right\rfloor} \varphi(it) \sum_^\right\rfloor} \varphi(jt)

\]發現這東西帶兩個引數,令

\[g(k, n) = \sum_^n \varphi(ik)

\]你有遞推式

\[g(k, n) = g(k, n - 1) + \varphi(nk)

\]而此處的 \(nk\le n\textsf n \textsf\),也可以 \(\theta(n\ln n)\) 預處理,\(g\) 陣列用vector存。

代回去\[ans = \sum_^n f(t) g\left(t, \left\lfloor\dfrac\right\rfloor \right) g\left(t, \left\lfloor\dfrac\right\rfloor \right)

\]這個 \(g\) 帶乙個 \(t\),無法整除分塊,只能暴力算。

此時是 \(\omicron(n\ln n)\) 的預處理,\(\omicron(n)\) 的單次回答,過不去。

設\[h(n, m, l) = \sum_^l f(t) g\left(t, n \right) g\left(t, m \right)

\]這樣在整除分塊中

\[h\left(\left\lfloor\dfrac\right\rfloor, \left\lfloor\dfrac\right\rfloor, r \right) - h\left(\left\lfloor\dfrac\right\rfloor, \left\lfloor\dfrac\right\rfloor, l - 1 \right)

\]又有遞推式

\[h(n, m, l) = h(n, m, l - 1) + f(l) g(l, n) g(l, m)

\]有 \(\max(n, m) l\le n \textsf n \textsf\)。

\(h\) 陣列同樣用vector存。

此時是\[\begin

\omicron\left(k \sum_^k \dfrac \right)

& = \omicron\left(k \cdot \int_1^k \dfrac \, dx \right) \\

& = \omicron(k\cdot n \ln k) \\

& = \omicron(nk \ln k)

\end

\]的預處理,\(\omicron(\sqrt)\) 的單次回答,預處理會 \(\text + \text\)。

既然兩種方法都不行,那麼自然想到用根號分治來平衡時間

設閾值為 \(k\),表示對於 \(\le k\) 的部分預處理。

於是當 \(\left\lfloor\dfrac\right\rfloor \le k\),即 \(l > \left\lfloor\dfrac\right\rfloor\) 的部分用已經預處理過的 \(h\) 整除分塊算,當 \(l \le \left\lfloor\dfrac\right\rfloor\) 時直接暴力算。

總時間複雜度為 \(\omicron\left(nk \ln k + t\left(\dfrac + \sqrt \right) \right)\),提個公因數就是 \(k\ln k + \dfrac\) 最小。

寫個程式去算

int t = 1e4;

int ans = 0x3f3f3f3f, pos = 0;

for (int k = 1; k <= t; k++) }

printf("%d %d\n", ans, pos);

輸出

392 47
所以取 \(k = 47\)。

空間複雜度為 \(\omicron(nk\ln k)\)。

然而實測 \(k\) 取 \(60\sim 70\) 更快(

// 18 = 9 + 9 = 18.

#include #include #include #define debug(x) cout << #x << "=" << x << endl

typedef long long ll;

using namespace std;

const int maxn = 1e5 + 5;

const int n = 1e5;

const int maxk = 47 + 5;

const int k = 47;

const int mod = 998244353;

typedef int arr[maxn];

int add(int a, int b)

int sub(int a, int b)

int mul(int a, int b)

int qpow(int a, int b)

base = (ll)base * base % mod;

b >>= 1;

} return ans;

}int inv(int a)

arr p, mu, phi, phi_pro, phi_pro_inv, phi_inv, f;

bool vis[maxn];

vectorg[maxn], h[maxk][maxk];

void pre()

for (int j = 1; j <= p[0] && i * p[j] <= n; j++)

mu[i * p[j]] = mod - mu[i];

phi[i * p[j]] = phi[i] * phi[p[j]];

} }phi_pro[0] = phi_inv[1] = 1;

for (int i = 1; i <= n; i++)

phi_pro_inv[n] = inv(phi_pro[n]);

for (int i = n - 1; i >= 1; i--)

for (int i = 1; i <= n; i++) }

for (int k = 1; k <= n; k++) }

for (int n = 1; n <= k; n++)

} }}

int block(int n, int m)

for (int l = m / k + 1, r; l <= n; l = r + 1)

return res;

}int main()

printf("%d\n", block(n, m));

} return 0;

}

P4240 毒瘤之神的考驗

p4240 毒瘤之神的考驗 假定 n leq m 交換n,m顯然不影響答案 首先尤拉函式有個性質。phi xy frac 代入題目 sum sum frac 然後是喜聞樂見的列舉公因數,在轉化為莫比烏斯函式。sum sum rfloor frac sum rfloor phi xtd sum rfl...

P4240 毒瘤之神的考驗

求 sum sum varphi ij 先要考慮怎麼把 varphi 轉成帶有 gcd 或 operatorname 的形式。性質 varphi ij frac 證明 begin varphi i varphi j i prod fracj prod frac p in primes ij prod...

題解 HNOI AHOI2018 毒瘤

題目傳送門 給出乙個 n 個點 m 條邊的無向圖,問有多少個點集滿足點集中任意兩點均不存在邊相連。n le 10 5,m n le 10 答案對 998244353 取模。妙啊!首先我們從樹的形態開始考慮,你發現答案其實就是獨立集的個數,具體來說我們可以設 f 表示 u 點選或不選的方案數,可以得到...