nyoj 92 图像有用区域 【BFS】 【好题 】

来源:互联网 发布:300663科蓝软件 编辑:程序博客网 时间:2024/04/28 06:43


图像有用区域

时间限制:3000 ms  |  内存限制:65535 KB
难度:4
描述

“ACKing”同学以前做一个图像处理的项目时,遇到了一个问题,他需要摘取出图片中某个黑色线圏成的区域以内的图片,现在请你来帮助他完成第一步,把黑色线圏外的区域全部变为黑色。

     

                图1                                                        图2 

已知黑线各处不会出现交叉(如图2),并且,除了黑线上的点外,图像中没有纯黑色(即像素为0的点)。

输入
第一行输入测试数据的组数N(0<N<=6)
每组测试数据的第一行是两个个整数W,H分表表示图片的宽度和高度(3<=W<=1440,3<=H<=960)
随后的H行,每行有W个正整数,表示该点的像素值。(像素值都在0到255之间,0表示黑色,255表示白色)
输出
以矩阵形式输出把黑色框之外的区域变黑之后的图像中各点的像素值。
样例输入
15 5100 253 214 146 120123 0 0 0 054 0 33 47 0255 0 0 78 014 11 0 0 0
样例输出
0 0 0 0 00 0 0 0 00 0 33 47 00 0 0 78 00 0 0 0 0
题目意思:在W*H矩阵有一个用0构成的圈,你需要把圈外的所有数字变成0,圈内不变。然后输出即可。 ac代码在最后面
咋看简单搜索嘛,果断DFS结果RTE 无语。。。 然后BFS各种错,下面是我AC过程中的错误,希望对你我都有帮助。
DFS  RTE代码:
#include <cstdio>#include <cstring>#include <algorithm>using namespace std;int map[964][1444];int H, W;int move[8][2] = {0,1, 0,-1, 1,0, -1,0};void getmap(){int i, j; for(i = 1; i <= H; i++){for(j = 1; j <= W; j++)scanf("%d", &map[i][j]);}}bool judge(int x, int y){return x >= 1 && x <= H && y >= 1 && y <= W && map[x][y]; }void DFS(int x, int y){map[x][y] = 0;for(int k = 0; k < 4; k++){int next_x = x + move[k][0];    int next_y = y + move[k][1];    if(judge(next_x, next_y))    {    DFS(next_x, next_y);    }} }void output(){for(int i = 1; i <= H; i++){for(int j = 1; j <= W; j++){if(j > 1) printf(" ");printf("%d", map[i][j]);}printf("\n");}} int main(){int t;scanf("%d", &t);while(t--){scanf("%d%d", &W, &H);getmap();DFS(1, 1);output();}return 0;}

没办法BFS吧: 结果又错了。
#include <cstdio>#include <cstring>#include <queue>#include <algorithm>using namespace std;int map[964][1444];int H, W;int move[8][2] = {0,1, 0,-1, 1,0, -1,0, 1,-1, -1,1, 1,1, -1,-1};struct Node{int x, y;};void getmap(){int i, j; for(i = 1; i <= H; i++){for(j = 1; j <= W; j++)scanf("%d", &map[i][j]);}}bool judge(int x, int y){return x >= 1 && x <= H && y >= 1 && y <= W && map[x][y]; }void BFS(int x, int y){Node now, next;queue<Node> Q;now.x = x;now.y = y;Q.push(now);while(!Q.empty()){now = Q.front();Q.pop();for(int k = 0; k < 8; k++){next.x = now.x + move[k][0];next.y = now.y + move[k][1];if(judge(next.x, next.y)){map[next.x][next.y] = 0;Q.push(next);}}}}void output(){for(int i = 1; i <= H; i++){for(int j = 1; j <= W; j++){if(j > 1) printf(" ");printf("%d", map[i][j]);}printf("\n");}} int main(){int t;scanf("%d", &t);while(t--){scanf("%d%d", &W, &H);getmap();BFS(1, 1);output();}return 0;}
仔细想想,方向搜多了比如这样的数据:
3 41 1 0 11 0 2 01 1 0 1 

正确答案:
0 0 0 0 0 0 2 00 0 0 0 

而我的代码输出是:
0 0 0 00 0 0 00 0 0 0 

改过之后继续。
结果又错了:
#include <cstdio>#include <cstring>#include <queue>#include <algorithm>using namespace std;int map[964][1444];int H, W;int move[4][2] = {0,1, 0,-1, 1,0, -1,0};struct Node{int x, y;};void getmap(){int i, j; for(i = 1; i <= H; i++){for(j = 1; j <= W; j++)scanf("%d", &map[i][j]);}}bool judge(int x, int y){return x >= 1 && x <= H && y >= 1 && y <= W && map[x][y]; }void BFS(int x, int y){Node now, next;queue<Node> Q;now.x = x;now.y = y;Q.push(now);while(!Q.empty()){now = Q.front();Q.pop();for(int k = 0; k < 4; k++){next.x = now.x + move[k][0];next.y = now.y + move[k][1];if(judge(next.x, next.y)){map[next.x][next.y] = 0;Q.push(next);}}}}void output(){for(int i = 1; i <= H; i++){for(int j = 1; j <= W; j++){if(j > 1) printf(" ");printf("%d", map[i][j]);}printf("\n");}} int main(){int t;scanf("%d", &t);while(t--){scanf("%d%d", &W, &H);getmap();BFS(1, 1);output();}return 0;}

真心醉了,好好想了想,发现有这样的数据:
3 30 0 10 1 00 0 0 
正确答案:
0 0 00 1 00 0 0 
我的代码输出:
0 0 10 1 00 0 0 

这也就是说如果直接BFS的话,还要考虑到边界为0的情况。因此我们应该在外面加一圈非0数,然后BFS。改了继续。
终于过了:
#include <cstdio>#include <cstring>#include <queue>#include <algorithm>using namespace std;int map[964][1444];int H, W;int move[4][2] = {0,1, 0,-1, 1,0, -1,0};struct Node{int x, y;};void getmap(){int i, j; for(i = 0; i <= H+1; i++){for(j = 0; j <= W+1; j++)map[i][j] = 1;} for(i = 1; i <= H; i++){for(j = 1; j <= W; j++)scanf("%d", &map[i][j]);}}bool judge(int x, int y){return x >= 0 && x <= H+1 && y >= 0 && y <= W+1 && map[x][y]; }void BFS(int x, int y){Node now, next;queue<Node> Q;now.x = x;now.y = y;Q.push(now);while(!Q.empty()){now = Q.front();Q.pop();for(int k = 0; k < 4; k++){next.x = now.x + move[k][0];next.y = now.y + move[k][1];if(judge(next.x, next.y)){map[next.x][next.y] = 0;Q.push(next);}}}}void output(){for(int i = 1; i <= H; i++){for(int j = 1; j <= W; j++){if(j > 1) printf(" ");printf("%d", map[i][j]);}printf("\n");}} int main(){int t;scanf("%d", &t);while(t--){scanf("%d%d", &W, &H);getmap();BFS(0, 0);output();}return 0;}


0 0