hdu1198并查集

来源:互联网 发布:淘宝差评在哪里解释 编辑:程序博客网 时间:2024/05/20 23:30

之前忘了并查集使用的方式,导致我把图中的11张图看成了各自的一类,然后就悲剧了=-=

简述这道题的意思,就是有11种suqare然后将这些可以组成各种大小的田地。现在它给你一块由这些suqare组成的田地

,因为每块地都有pipe,要保证这些田都被灌溉你要判断这块地需要多少个wellspring。

首先说下并查集的思路:题目要求是输入m行,n列,而且m和n是不超过50,算出来是2500,说明使用并查集是可以解决的

时间复杂度是O(m*n),并查集最需要注意的地方就是要注意初始化。这道题wa了4次,前两次是没找出自己的并查集是写错的

,后两次改成正确的并查集,然而却忘了初始化_(:зゝ∠)_。

#include<iostream>#include<fstream>#include<cstring>using namespace std;struct Squares{    bool up;    bool down;    bool left;    bool right;    int root;};int p[2510];Squares S[12];int disjoint[12] = { 0 };bool isjudge[2510] = { 0 };int m, n;int map[60][60];void init(){    S[1].up = true;    S[1].down = false;    S[1].left = true;    S[1].right = false;    S[1].root = 1;    S[2].up = true;    S[2].down = false;    S[2].left = false;    S[2].right = true;    S[2].root = 2;    S[3].up = false;    S[3].down = true;    S[3].left = true;    S[3].right = false;    S[3].root = 3;    S[4].up = false;    S[4].down = true;    S[4].left = false;    S[4].right = true;    S[4].root = 4;    S[5].up = true;    S[5].down = true;    S[5].left = false;    S[5].right = false;    S[5].root = 5;    S[6].up = false;    S[6].down = false;    S[6].left = true;    S[6].right = true;    S[6].root = 6;    S[7].up = true;    S[7].down = false;    S[7].left = true;    S[7].right = true;    S[7].root = 7;    S[8].up = true;    S[8].down = true;    S[8].left = true;    S[8].right = false;    S[8].root = 8;    S[9].up = false;    S[9].down = true;    S[9].left = true;    S[9].right = true;    S[9].root = 9;    S[10].up = true;    S[10].down = true;    S[10].left = false;    S[10].right = true;    S[10].root = 10;    S[11].up = true;    S[11].down = true;    S[11].left = true;    S[11].right = true;    S[11].root = 11;}void initroot(){    for (int i = 0; i <= m*n; i++)    {        p[i] = i;    }}int findroot(int a){    int root = a;    while (p[root] != root)        root = p[root];    int i = a, j;    while (i != root)    {        j = p[i];        p[i] = root;        i = j;    }    return root;}void merge(int a, int b){    int fx = findroot(a), fy = findroot(b);    if (fx != fy)    {        p[fx] = fy;    }}int ans;void solve(){    ans = 0;    int loc;    int locup;    int locdown;    int locleft;    int locright;    for (int i = 0; i < m; i++)    {        for (int j = 0; j < n; j++)        {            loc = map[i][j];            if (i - 1 >= 0)//up is right            {                locup = map[i - 1][j];                if (S[locup].down&&S[loc].up)                {                    merge(i*n + j, (i - 1)*n + j);                }            }            if (i + 1 < m)//down is right            {                locdown = map[i + 1][j];                if (S[locdown].up&&S[loc].down)                {                    merge(i *n + j, (i + 1)*n + j);                }            }            if (j + 1 < n)//right is right            {                locright = map[i][j + 1];                if (S[locright].left&&S[loc].right)                {                    merge(i *n + j, i*n + j + 1);                }            }            if (j - 1 >= 0)            {                locleft = map[i][j - 1];                if (S[locleft].right&&S[loc].left)                {                    merge(i*n + j, i*n + j - 1);                }            }        }    }    for (int i = 0; i < m*n; i++)        findroot(i);    for (int i = 0; i < m*n; i++)    {        if (isjudge[p[i]] == false)        {            ans++;            isjudge[p[i]] = true;        }    }    printf("%d\n", ans);}int main(){    init();    while (scanf_s("%d%d", &m, &n))    {        //getchar();        initroot();        memset(isjudge, false, sizeof(isjudge));        memset(map, 0, sizeof(map));        if (m + n == -2)            break;        char c;        for (int i = 0; i < m; i++)        {            for (int j = 0; j < n; j++)            {                cin >> c;                //scanf_s("%c", &c);                map[i][j] = c - 'A' + 1;            }            //getchar();        }        solve();    }}

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 猫在外面躲起来找不到了怎么办 本科三批取消以后三本学校怎么办 机票名字多了个字母安检怎么办 出隧道口限速40超速了怎么办 社保交了五年后断交以后该怎么办 躺椅折叠椅坐的地方坏了怎么办 苹果手机锁频密码忘了怎么办 客户要货公司不给进怎么办 高铁23:00买的票怎么办 带电子手刹的车刹车失灵怎么办 下坡刹车失灵遇行人不看车怎么办 跟大车后面看不见红灯闯了怎么办 跟着大货车后面闯了红灯怎么办 如果用工单位不发放加班工资怎么办 事故家属要司机向医院多交钱怎么办 在大学里和室友关系弄僵怎么办 房产证办出来房产局不给证怎么办 单位全员竞聘老员工没岗位怎么办 快件被快递公司签收了没给送怎么办 总公司跑路了分公司代理法人怎么办 大使馆领的结婚证现在离婚怎么办 日本签证照片被使馆贴错了怎么办 在菲律宾护照和签证丢了怎么办 新疆工地上班老板不肯发工资怎么办 德国大使馆签证如果拒签了怎么办 护照在大使馆办签证期间出国怎么办 法院两次判决不准离婚我该怎么办? 法院判决不准离婚妻子不回来怎么办 被告人在不调解的情况下怎么办 知道弟兄的孩子是别人的怎么办? 办居住证的回执单丢了怎么办 领取居住证的回执单丢了怎么办 北京居住证网上申报信息填错怎么办 买家退回来的货有问题怎么办 居转户过程中生的小孩户口怎么办 人才引进申请上海户口被拒怎么办 网络购高铁票身份证没有验证怎么办 高速遇到很浓的团雾怎么办 对于大巴不按座位坐的人该怎么办 火车上遇到占座不让的人怎么办 滁州婴儿打疫苗的绿本子怎么办