Codeforces Round #500 (Div. 2) D Chemical table

翻译

给你一个图,这个图里面会有一些长方形与正方形,只要他们的四角中的任意三个角有一个\(X\)的话(请饶恕我这么形容),那么他就会在空缺的角形成一个新的\(X\),你可以变出来一个\(X\),给你这个图的大小以及哪里有\(X\),问你至少要变出几个\(X\)才可以使得全图都是\(X\)。

思路

不亏是明星团队出的题,代码量不大但是思维坑啊。那么我就不绕了,直接入正题(听说有人五分钟切了这道题?)

这道题熟练图论的人可能会想到办法,按照套路,我们可以把有\(X\)的格子他们的行和列看为两个点,然后把全图跑一边,这样会形成一个图,那么这个图会长啥样?

我们先弄一下\(2*2\)的,假设他三个角都有了\(X\)。那么可能是长下面的一种。

感觉到了什么,没错,这个图是联通的啊!只要有三个边四个点(四个点是格子的四角)一定是联通的!而且加不加第四个已经无所谓了?是不是?我们再以\(2*2\)为例子,看看只有两个边的情况。

你可以容易的想到无论只有两个边或一个边或没有(一个边是一个\(X\)哦!),都不是联通的,这个时候,我们就想帮他联通。建一条边的话要变一次\(X\),一直到整个图联通为止。就像,上图,每个加一个\(X\)就好了,因此答案是\(1\)

我们再上一下样例的图(上面是行,下面是列):

答案是\(1\),你就会想,这不是要加两条边吗??

这就怪了??但是你仔细一想啊,上面两个图的联通块个数都是二,答案都是一!没错是联通块的个数再减一!!!

至此,我很啰嗦的啰嗦完了这道看上去啰嗦但是思想好代码不啰嗦的啰嗦题目,下面是超短代码,我竟然会给注释。

Code

#include<bits/stdc++.h>
using namespace std;
int n,m,q;
bool vis[500010];
vector<int>e[500010];

void dfs(int u)//最简单的求联通分量
{
    vis[u]=1;
    int sz=e[u].size();
    for(int i=0;i<sz;i++)
        if(!vis[e[u][i]])
            dfs(e[u][i]);
}

int x, y,ans;
int main ()
{
    cin>>n>>m>>q;
    while(q--)
        cin>>x>>y, e[x].push_back(y+n), e[y+n].push_back(x);//为了好搜,于是行正常,列要加上X的个数
    for(int i=1;i<=n+m;i++)
        if(!vis[i]) ans++, dfs(i);//统计答案
    cout<<ans-1<<endl;
    return 0;
}

原文地址:https://www.cnblogs.com/lyfoi/p/9485074.html

时间: 2024-09-30 00:45:56

Codeforces Round #500 (Div. 2) D Chemical table的相关文章

Codeforces Round #500 (Div. 2) [based on EJOI]

Codeforces Round #500 (Div. 2) [based on EJOI] https://codeforces.com/contest/1013 A 1 #include<bits/stdc++.h> 2 using namespace std; 3 #define lson l,mid,rt<<1 4 #define rson mid+1,r,rt<<1|1 5 #define IT set<node>::iterator 6 #def

Codeforces Round #500 (Div. 2) 游记

A Piles With Stones 题意 有\(N\)堆石子,任意个人.每个人可以把一堆石子中的一个石子移动到另一堆,或者是拿走一堆石子.现在给你石子一开始的情况与这些人进行操作后的情况,问是否合法. 思路 此题看上去不简单,但是你可能在几秒内想出一个结论,那就是:无论这些人怎么移动,都没有办法使得石子数量增多!那么做法就简单了,如果石子数量比没改动前的多,那么就不合法了. Code #include<iostream> using namespace std; int sum1=0,su

Codeforces Round #256 (Div. 2) D. Multiplication Table(二分查找)

转载请注明出处:http://blog.csdn.net/u012860063?viewmode=contents 题目链接:http://codeforces.com/contest/448/problem/D -----------------------------------------------------------------------------------------------------------------------------------------------

Codeforces Round #323 (Div. 2) C. GCD Table

C. GCD Table The GCD table G of size n × n for an array of positive integers a of length n is defined by formula Let us remind you that the greatest common divisor (GCD) of two positive integers x and y is the greatest integer that is divisor of both

Codeforces Round #140 (Div. 1)D The table 贪心

#include<iostream> #include<cstdio> #include<cstring> using namespace std ; const int maxn = 110 ; int sum_r[maxn] ; int sum_c[maxn] ; int vis_c[maxn] ;int vis_r[maxn] ; int ans_c[maxn] ;int ans_r[maxn] ; int table[maxn][maxn] ; void ini

Codeforces Round #256 (Div. 2) D. Multiplication Table

Bizon the Champion isn't just charming, he also is very smart. While some of us were learning the multiplication table, Bizon the Champion had fun in his own manner. Bizon the Champion painted an n?×?m multiplication table, where the element on the i

Codeforces Round #500 (Div. 2) BC

CodeForces 1013B And CodeForces 1013C  Photo of The Sky B 可以发现只有一次与操作是有意义的,所以答案只有-1,0,1,2四种情况 1 #include <bits/stdc++.h> 2 #define show(a) cout << #a << " = " << a << endl; 3 const int MOD = 1e9+7; 4 const int MAXN

Codeforces Round #243 (Div. 2)——Sereja and Table

看这个问题之前,能够先看看这个论文<一类算法复合的方法>,说白了就是分类讨论,可是这个思想非常重要 题目链接 题意: 首先给出联通块的定义:对于相邻(上下和左右)的同样的数字视为一个联通块 现给一个n*m的仅仅有0和1的矩形和数字k,求出最小反转个数使得总体包含若干个矩形联通块(即每一个联通块均是矩形)(1?≤?n,?m?≤?100; 1?≤?k?≤?10) 假设最小次数比k大,输出-1 分析: 题目的特点是k比較小.也就是说反转的次数比較少,所以能够从这里入手.直接枚举全部的位置肯定是不行了

Codeforces Round#500 Div.2 翻车记

A:签到 #include<iostream> #include<cstdio> #include<cmath> #include<cstdlib> #include<cstring> #include<algorithm> using namespace std; int read() { int x=0,f=1;char c=getchar(); while (c<'0'||c>'9') {if (c=='-') f=