zoukankan      html  css  js  c++  java
  • [CH2601] 电路维修 题解

    描述

    Ha'nyu是来自异世界的魔女,她在漫无目的地四处漂流的时候,遇到了善良的少女Rika,从而被收留在地球上。Rika的家里有一辆飞行车。有一天飞行车的电路板突然出现了故障,导致无法启动。
    电路板的整体结构是一个R行C列的网格(R,C≤500),如右图所示。每个格点都是电线的接点,每个格子都包含一个电子元件。电子元件的主要部分是一个可旋转的、连接一条对角线上的两个接点的短电缆。在旋转之后,它就可以连接另一条对角线的两个接点。电路板左上角的接点接入直流电源,右下角的接点接入飞行车的发动装置。

    Ha'nyu发现因为某些元件的方向不小心发生了改变,电路板可能处于断路的状态。她准备通过计算,旋转最少数量的元件,使电源与发动装置通过若干条短缆相连。不过,电路的规模实在是太大了,Ha'nyu并不擅长编程,希望你能够帮她解决这个问题。

    输入格式

    输入文件包含多组测试数据。第一行包含一个整数T 表示测试数据的数目。
    对于每组测试数据,第一行包含正整数R 和C,表示电路板的行数和列数。
    之后R 行,每行C 个字符,字符是"/"和""中的一个,表示标准件的方向。

    输出格式

    对于每组测试数据,在单独的一行输出一个正整数,表示所需的缩小旋转次数。
    如果无论怎样都不能使得电源和发动机之间连通,输出NO SOLUTION。

    样例输入

    1
    3 5
    /
    ///
    /\
    样例输出

    1
    数据范围与约定

    对于40% 的数据,R,C≤5。
    对于100% 的数据,R,C≤500,T≤5。
    样例解释

    样例的输入对应于题目描述中的情况。
    只需要按照下面的方式旋转标准件,就可以使得电源和发动机之间连通。

    来源

    杜宇飞,石家庄二中【Nescafé 5】杯NOIP模拟赛


    思路:考虑BFS,从左上角开始搜索,显然当边长一奇一偶时无法走到右下角,且左上 右下角一定为''.则可以按照每个格子保存的斜线方向往当前格子的四周bfs,判断是否需要改变.用介质为当前旋转次数的优先队列维护BFS即可
    代码

    #include <algorithm>
    #include <iostream>
    #include <cstring>
    #include <cstdio>
    #include <cmath>
    #include <queue>
    #include <stack>
    #include <set>
    #include <map>
    using namespace std;
    #define rg register
    #define LL long long
    #define __space putchar(' ')
    #define __endl putchar('
    ')
    template <typename qwq> inline void read(qwq & x)
    {
        x = 0;
        rg int f = 1;
        rg char c = getchar();
        while (c < '0' || c > '9')
        {
            if (c == '-') f = -1;
            c = getchar();
        }
        while (c >= '0' && c <= '9')
        {
            x = (x << 1) + (x << 3) + (c ^ 48);
            c = getchar();
        }
        x *= f;
    }
    template <typename qaq> inline void print(qaq x)
    {
        if (x < 0)
        {
            putchar('-');
            x = -x;
        }
        if (x > 9) print(x / 10);
        putchar(x % 10 + '0');
    }
    char Map[2333][2333];
    int n,m,t;
    int ans[2333][2333];
    int dx[] = {0,0,1,1,0,-1,-1,-1,1};
    int dy[] = {0,1,0,1,-1,0,-1,1,-1};
    //1:右 2:下 3:右下 4:左 5:上 6:左上 7:右上 8:左下 
    struct node
    {
    	int w,x,y;
    	char c;
    	friend bool operator < (const node a,const node b)
    	{
    		return a.w > b.w;
    	}
    }start;
    priority_queue<node>heap;
    //first:cost second:point 
    inline void prework()
    {
    	while(!heap.empty()) heap.pop();
    	for (rg int i = 1;i <= n;++i)
    	{
    		for (rg int j = 1;j <= m;++j)
    		{
    			ans[i][j] = 0x7f7f7f7f;
    		}
    	}
    	ans[1][1] = 0;
    }
    #define you 1
    #define xia 2
    #define youxia 3
    #define zuo 4
    #define shang 5
    #define zuoshang 6
    #define youshang 7
    #define zuoxia 8
    inline void boy_friend_search()
    {
    	heap.push(start);
    	while (!heap.empty())
    	{
    		rg node now = heap.top();
    		rg int x = now.x,y = now.y;
    		rg char c = now.c;
    		heap.pop();
    		for (rg int i = 1;i <= 8;++i)
    		{
    			rg int nx = x + dx[i],ny = y + dy[i];
    			rg char nc;
    			if (nx < 1 || nx > n || ny < 1 || ny > m) continue;
    			if (i == zuo || i == you || i == shang || i == xia)// 向左/右/上/下走 
    			{
    				if (c == Map[nx][ny])//如果两个相同的话 
    				{
    					//若要保证联通则必须更改 
    					if (ans[x][y] + 1 < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y] + 1;
    //						nc = (Map[x][y] == '/') ? 92 : '/';
    						if (c == '/') nc = 92;
    						else nc = '/';
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,nc});
    					}
    				}
    				else
    				{
    					//否则不需要更改 
    					if (ans[x][y] < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y];
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,Map[nx][ny]});
    					}
    				}
    			}
    			else if (i == zuoshang || i == youxia)//向 左上/右下 
    			{
    				if (c == '/') continue;
    				if (c != Map[nx][ny])//如果两个不同的话 
    				{
    					//若要保证联通则必须更改 
    					if (ans[x][y] + 1 < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y] + 1;
    						nc = c;
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,nc});
    					}
    				}
    				else
    				{
    					//否则不需要更改 
    					if (ans[x][y] < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y];
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,Map[nx][ny]});
    					}
    				}
    			}
    			else// 左下/右上 
    			{
    				if (c == 92) continue;
    				if (c != Map[nx][ny])//如果两个不同的话 
    				{
    					//若要保证联通则必须更改 
    					if (ans[x][y] + 1 < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y] + 1;
    						nc = c;
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,nc});
    					}
    				}
    				else
    				{
    					//否则不需要更改 
    					if (ans[x][y] < ans[nx][ny])
    					{
    						ans[nx][ny] = ans[x][y];
    						if (nx == n && ny == m) return;
    						heap.push((node) {ans[nx][ny],nx,ny,Map[nx][ny]});
    					}
    				}
    			}
    		}
    	}
    }
    int main()
    {
    	start.x = 1,start.y = 1,start.c = 92;
    	read(t);
    	while (t--)
    	{
    		read(n),read(m);
    		prework();
    		for (rg int i = 1;i <= n;++i) scanf("%s",Map[i] + 1);
    		if (Map[1][1] == '/') ++ans[1][1],Map[1][1] = 92;//ASCII
    		start.w = ans[1][1];
    		if ((n & 1) && !(m & 1))
    		{
    			puts("NO SOLUTION");
    			continue;
    		}
    		if (!(n & 1) && (m & 1))
    		{
    			puts("NO SOLUTION");
    			continue;
    		}
    		boy_friend_search();
    		print(ans[n][m]),__endl;
    	}
    	return 0;
    }
    
  • 相关阅读:
    【iOS】js调用oc的一个注意点
    【iOS】程序内跳转到支付宝转账(非SDK实现支付)及相关监听
    GCD定时器不走set_event_handler和variable is not assignable missing block
    苹果审核上传附件上传不上去
    上传本地代码到gitHub过程详解
    iOS---学习研究大牛Git高星项目YYCategories(四)
    iOS 关键字const/static/extern、UIKIT_EXTERN区别和用法
    iOS---学习研究大牛Git高星项目YYCategories(三)
    iOS---学习研究大牛Git高星项目YYCategories(二)
    iOS---学习研究大牛Git高星项目YYCategories(一)
  • 原文地址:https://www.cnblogs.com/Here-is-SG/p/10519274.html
Copyright © 2011-2022 走看看