2021牛客暑期多校训练营#6:C-Delete Edges
原题题解:https://ac.nowcoder.com/acm/contest/11257/C
文章目录
- 2021牛客暑期多校训练营#6:C-Delete Edges
-
- 题目大意
- 解题思路
-
- 拓展时间
-
- 矩阵快速幂
- 数学
- 代码实现
题目大意
给定一个有 n ( 3 ≤ n ≤ 2000 ) n(3\leq n\leq 2000) n(3≤n≤2000)个点的完全图,j节点编号从 1 1 1到 n n n,你可以多次删除图上的边,每次选择三个节点 x , y , z x,y,z x,y,z,其中 ( x , y ) (x,y) (x,y) ( x , z ) (x,z) (x,z) ( y , z ) (y,z) (y,z)并未被删除,然后删除这三条边。
求使得剩余边数小于 n n n的删边方案。
解题思路
做题胆要大,什么结论都往上套
首先,证明当 x + y + z ≡ 0 ( m o d n ) x+y+z\equiv0(\bmod\ n) x+y+z≡0(mod n)且 x < y < z x <y<z x<y<z时删边不会重复。
当 x + y + z = n x+y+z=n x+y+z=n时 ( x + 1 ) + ( y + 1 ) + ( z + 1 ) = n + 3 (x+1)+(y+1)+(z+1)=n+3 (x+1)+(y+1)+(z+1)=n+3
x | 1 | 1 | 1 | … \ldots … | 1 |
---|---|---|---|---|---|
y | 2 | 3 | 4 | … \ldots … | 偶: n 2 \frac{n}{2} 2n?·奇: ? n + 2 2 ? \lfloor\frac{n+2}{2}\rfloor ?2n+2?? |
z | n | n-1 | n-2 | … \ldots … | 偶: n + 4 2 \frac{n+4}{2} 2n+4?·奇: ? n + 2 2 ? \lfloor\frac{n+2}{2}\rfloor ?2n+2?? |
一共有 ? n ? 1 2 ? \lfloor\frac{n-1}{2}\rfloor ?2n?1??个。
当 x + y + z = 2 n x+y+z=2n x+y+z=2n时 ( x + 1 ) + ( y + 1 ) + ( z + 1 ) = 2 ( n + 3 ) (x+1)+(y+1)+(z+1)=2(n+3) (x+1)+(y+1)+(z+1)=2(n+3),而当 z = n + 2 z=n+2 z=n+2时,
z | n+3 | n+3 | n+3 | … \ldots … |
---|---|---|---|---|
x | 1 | 2 | 3 | … \ldots … |
y | n | n-1 | n-2 | … \ldots … |
共有 ? n 2 ? + 1 \lfloor \frac{n}{2}\rfloor+1 ?2n??+1个。
得出递推式
f ( n + 3 ) = f ( n ) + ? n ? 1 2 ? + ? n 2 ? + 1 = f ( n ) + { n ? 1 2 + n ? 1 2 + 1 ( n % 2 = = 1 ) n 2 + n ? 2 2 + 1 ( n % 2 = = 0 ) = f ( n ) + n \begin{aligned} f(n+3)&=f(n)+\lfloor\frac{n-1}{2}\rfloor+\lfloor \frac{n}{2}\rfloor+1\\ &=f(n)+ \left\{ \begin{array}{rcl} &\frac{n-1}{2}+\frac{n-1}{2}+1&(n\%2==1)\\ &\frac{n}{2}+\frac{n-2}{2}+1&(n\%2 ==0) \end{array} \right.\\ &=f(n)+n \end{aligned} f(n+3)?=f(n)+?2n?1??+?2n??+1=f(n)+{
?2n?1?+2n?1?+12n?+2n?2?+1?(n%2==1)(n%2==0)?=f(n)+n?
之后枚举 x , y x,y x,y,算出 z z z,可AC。
拓展时间
本题范围不大,但如果达到 1 0 9 10^9 109,暴力就肯定超时,以下是两种解法。
矩阵快速幂
我们老师说:大部分线性变换都可以用矩阵快速幂来做
首先写出矩阵 [ f ( n ) f ( n ? 1 ) f ( n ? 2 ) n ? 2 1 ] \begin{bmatrix} f(n) \\ f(n-1) \\ f(n-2)\\ n-2 \\ 1 \end{bmatrix} ???????f(n)f(n?1)f(n?2)n?21????????
写出等式
[ f ( n + 1 ) f ( n ) f ( n ? 1 ) n ? 1 1 ] = [ 0 0 1 1 0 1 0 0 0 0 0 1 0 0 0 0 0 0 1 1 0 0 0 0 1 ] [ f ( n ) f ( n ? 1 ) f ( n ? 2 ) n ? 2 1 ] \begin{bmatrix} f(n+1) \\ f(n) \\ f(n-1)\\ n-1\\ 1 \end{bmatrix}= \begin{bmatrix} &0&0&1&1&0&\\ &1&0&0&0&0\\ &0&1&0&0&0\\ &0&0&0&1&1\\ &0&0&0&0&1 \end{bmatrix} \begin{bmatrix} f(n) \\ f(n-1) \\ f(n-2)\\ n-2 \\ 1 \end{bmatrix} ???????f(n+1)f(n)f(n?1)n?11????????=????????01000?00100?10000?10010?00011???????????????f(n)f(n?1)f(n?2)n?21????????
最后矩阵快速幂求得方案数。
数学
我们由上得知 n ( n ? 1 ) 2 ? 2 f ( n ) < n 3 f ( n ) > n ( n ? 1 ) 2 ? n f ( n ) > n ( n ? 3 ) 6 \begin{aligned} \frac{n(n-1)}{2}-2f(n)&<n\\ 3f(n)&>\frac{n(n-1)}{2}-n\\ f(n)&>\frac{n(n-3)}{6} \end{aligned} 2n(n?1)??2f(n)3f(n)f(n)?<n>2n(n?1)??n>6n(n?3)??
当 n m o d 3 = 0 n\bmod3=0 nmod3=0:
f ( 3 ) + 3 = f ( 6 ) , f ( 6 ) + 6 = f ( 9 ) , f ( 9 ) + 9 = f ( 12 ) … f(3)+3=f(6),f(6)+6=f(9),f(9)+9=f(12)\ldots f(3)+3=f(6),f(6)+6=f(9),f(9)+9=f(12)…
可知为等差数列。
可得当 n m o d 3 = 0 n\bmod3=0 nmod3=0:
f ( n ) = ( n 2 ? 3 n + 3 ) ( n ? 1 ) 6 + 1 f(n)=\frac{(n^2-3n+3)(n-1)}{6}+1 f(n)=6(n2?3n+3)(n?1)?+1
其它情况亦可推出。
写出通项式:
f ( n ) = { n 2 ? 3 n + 3 6 > n ( n ? 3 ) 6 ( n % 3 = = 0 ) n 2 ? 3 n + 3 6 > n ( n ? 3 ) 6 ( n % 3 ! = 0 ) f(n)= \left\{ \begin{array}{rcl} \frac{n^2-3n+3}{6}&>\frac{n(n-3)}{6}&(n\%3==0)\\ \frac{n^2-3n+3}{6}&>\frac{n(n-3)}{6}&(n\%3 !=0) \end{array} \right. f(n)={
6n2?3n+3?6n2?3n+3??>6n(n?3)?>6n(n?3)??(n%3==0)(n%3!=0)?
代码实现
#include<bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false),cin.tie(0),cout.tie(0); int n,ans=0;cin>>n;if(n%3==0)ans=n*n-3*n+6;elseans=n*n-3*n+2;ans/=6;cout<<ans<<'\n';for(int i=0;i<n;i++){
for(int j=i+1;j<n;j++){
int k=(2*n-i-j)%n;if(j<k)cout<<i+1<<' '<<j+1<<' '<<k+1<<'\n';}}
}