题解 签到题
结论:度数是 \(c\) 的倍数的点的贡献为 0,其余的点的贡献为 1
貌似猜结论比证明更好做
- 关于图的染色:这里
放个链接跑路吧:这里和这里
证明过程大意(好像)是先将每个点都尽量拆成度数为 \(c\) 的点
由Vizing定理知这些度数为 \(c\) 的点一定能完成染色
然后那些差一点不到 \(c\) 的就产生1的贡献
Code:
#include <bits/stdc++.h>
using namespace std;
#define INF 0x3f3f3f3f
#define N 1000010
#define ll long long
#define fir first
#define sec second
#define make make_pair
//#define int long long
char buf[1<<21], *p1=buf, *p2=buf;
#define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf, 1, 1<<21, stdin)), p1==p2?EOF:*p1++)
inline int read() {
int ans=0, f=1; char c=getchar();
while (!isdigit(c)) {if (f=='-') f=-f; c=getchar();}
while (isdigit(c)) {ans=(ans<<3)+(ans<<1)+(c^48); c=getchar();}
return ans*f;
}
int n, m, k, c;
namespace task1{
int sta1[N], top1, sta2[N], top2, ans=INF;
int cnta[N], cntb[N];
int acol1[N], acol0[N], bcol1[N], bcol0[N];
pair<int, int> e[N];
void solve() {
for (int i=1,a,b; i<=k; ++i) {
a=read(); b=read();
e[i]=make(a, b);
++cnta[a]; ++cntb[b];
}
for (int i=1; i<=n; ++i) if (cnta[i]) sta1[++top1]=i;
for (int i=1; i<=m; ++i) if (cntb[i]) sta2[++top2]=i;
int lim=1<<k;
for (int s=0; s<lim; ++s) {
int sum=0;
for (int i=1; i<=top1; ++i) acol1[sta1[i]]=acol0[sta1[i]]=0;
for (int i=1; i<=top2; ++i) bcol1[sta2[i]]=bcol0[sta2[i]]=0;
for (int i=0; i<k; ++i) {
if (s&(1<<i)) {
++acol1[e[i+1].fir]; ++bcol1[e[i+1].sec];
}
else {
++acol0[e[i+1].fir]; ++bcol0[e[i+1].sec];
}
}
for (int i=1; i<=top1; ++i) sum+=max(acol1[sta1[i]], acol0[sta1[i]])-min(acol1[sta1[i]], acol0[sta1[i]]);
for (int i=1; i<=top2; ++i) sum+=max(bcol1[sta2[i]], bcol0[sta2[i]])-min(bcol1[sta2[i]], bcol0[sta2[i]]);
ans=min(ans, sum);
}
printf("%d\n", ans);
exit(0);
}
}
namespace task{
int cnta[N], cntb[N], ans;
void solve() {
for (int i=1,a,b; i<=k; ++i) {
a=read(); b=read();
++cnta[a]; ++cntb[b];
}
for (int i=1; i<=n; ++i) ans+=(cnta[i]%c!=0);
for (int i=1; i<=m; ++i) ans+=(cntb[i]%c!=0);
printf("%d\n", ans);
exit(0);
}
}
signed main()
{
freopen("qiandao.in", "r", stdin);
freopen("qiandao.out", "w", stdout);
n=read(); m=read(); k=read(); c=read();
// if (c==1) {puts("0"); return 0;}
// else if (c==2) task1::solve();
task::solve();
return 0;
}