例题6-13Ancient Messages UVA1103 dfs求连通块+16进制转2进制

来源:互联网 发布:数据库中union all 编辑:程序博客网 时间:2024/05/22 14:25

题目链接:https://vjudge.net/problem/UVA-1103

题意:给出几种象形符号,然后给出16进制的像素描述,让你根据描述字典序输出描述中的象形符号。

思路:几种象形符号可以转化成不同的连通块个数。先转换16进制为2进制,然后给图形外面加一层“边框”0,第一次dfs遍历将外面多余的0全部变成 ‘ - ’ ,然后再进行dfs遇到‘1’就找它是否包围0,包围了几个就对应相应的象形符号。最后字典序输出。


Code:

#include <iostream>#include <cstdio>#include <map>#include <string.h>using namespace std;const int maxn = 1e3+6;char G[maxn][maxn];char s[8] = { 'W' , 'A' , 'K' , 'J' , 'S' , 'D' };//0 1 2 3 4 5const char t[8] = { 'A' , 'D' , 'J' ,'K' ,'S','W' };map<char,int>mp;int H , W , ans ;int dir[8][2] = {{1,0},{0,1},{0,-1},{-1,0},};string dic[16] = {"0000" , "0001" , "0010", "0011","0100" , "0101" , "0110", "0111","1000" , "1001" , "1010", "1011","1100" , "1101" , "1110", "1111",};bool judge( int r,  int c){return r >= 0 && r <= H + 1 && c >= 0 && c <= W + 1;}void DFS1( int r,  int c){if (!judge(r, c) || G[r][c]!='0') return;G[r][c] = '-';for (int i = 0; i < 4; ++i)DFS1(r + dir[i][0], c + dir[i][1]);}void DFS( int r , int c ){if(!judge(r,c) || G[r][c] != '1' ) return ;G[r][c] = '-';for( int i = 0 ; i < 4 ; i++ ){int rr = r + dir[i][0] ,  cc = c + dir[i][1];if( G[rr][cc] == '0' ){ans ++ ;DFS1(rr,cc);}else{DFS(rr,cc);}}}int main(){int Case = 0;;while( ~scanf("%d%d",&H,&W) && H || W ){memset(G,'0',sizeof(G));mp.clear();W *= 4;for( int i = 1 ; i <= H ; i++ ){string line , tmp ;cin >> line;int len = line.size();for( int j = 0 ; j < len ; j++ ){tmp += dic[ isalpha(line[j]) ? line[j] - 'a' +10 : line[j] - '0' ];}memcpy( G[i]+1 , tmp.c_str() , W );}DFS1( 0 , 0 );/*for( int i = 0 ; i <= H + 1 ; i++ ){for( int j = 0 ; j <= W +1; j++ ){cout << G[i][j] ;}cout << endl;}*/for( int i = 1 ; i <= H ; i++ ){for( int j = 1 ; j <= W ; j++ ){if( G[i][j] == '1' ){ans = 0 ;DFS( i ,  j );mp[s[ans]]++;}}}cout << "Case " << ++Case << ": ";for( int i = 0 ; i < 6 ; i++ ){while( mp[t[i]] ){mp[t[i]] --;cout << t[i] ;}}cout << endl;}return 0;}
一题写了一上午。。。要加油了。。

原创粉丝点击