您的位置:首页 > 其它

经典算法之传染病问题 递归用法学习

2013-05-22 19:40 537 查看
问题描述:一个坐标表格,每个单元表格就代表一个地方有传染病病毒存在。

无病毒的地方用0标记,有病毒的地方用1标记。(为了方便表示边界,我在周围加了个-1的墙壁)

而我们实际常常研究的是估算受感染程度,该程序需要在接收一个坐标为输入后以该点为中心向周围的8个方向进行递归拓展,检查周围区域是否被感染。得到的菌群用2来标记。类似的应用有图像处理上的ps可以用这个算法找出某种颜色值的分布。

 

然后要考虑到边界问题:遇到边界应当终止递归。另外还要排除已经访问过的点,即遇到的话也退出递归。

对此我用了个结构体node描述每个区域,offset结构体描述方向。

下面是我的代码:

#include <iostream>
using namespace std;
struct node
{
int  value;        // 值为0 无毒,-1(边界墙壁), 1有毒
bool bCheck;
int  findvirus;    // 发现了有病毒,就给标记为1;
};
struct offset
{
int x;
int y;
};

offset  move[9];
// 本来是6的,但是为了加一层的墙壁,就变8了,墙壁上的值为-1,没有检查为0,检查了为1
node array[8][8]; // 没有病毒为0,有病毒为1

void InitArray()
{
// 先初始化(墙壁-1,没有病毒为0,有为1) 刚开始的话所有都是未被访问的。应为被我memset为0了呗。。。
memset(array,0, sizeof(node)*64);
for (int i=0;i<8;i++)
{
array[i][0].value=-1;
array[0][i].value=-1;
array[7][i].value=-1;
array[i][7].value=-1;
}
array[1][1].value=1;
array[2][2].value=1;
array[3][3].value=1;
array[3][4].value=1;
array[3][6].value=1;
array[4][4].value=1;
array[4][3].value=1;
array[4][6].value=1;
array[5][1].value=1;
array[5][3].value=1;
array[5][4].value=1;
array[5][6].value=1;
array[6][1].value=1;

/////////////////
move[0].x=0;    // 不动 自己的位置
move[0].y=0;
move[1].x=0;
move[1].y=-1;   // N
move[2].x=1;    // NE
move[2].y=-1;
move[3].x=1;    //  E
move[3].y=0;
move[4].x=1;    //  ES
move[4].y=1;
move[5].x=0;    // S
move[5].y=1;
move[6].x=-1;   //WS
move[6].y=1;
move[7].x=-1;   // W
move[7].y=0;
move[8].x=-1;   // WN
move[8].y=-1;

}
void ShowInitValue()
{
for (int i=0;i<8;i++)
{
for (int j=0;j<8;j++)
{
if (array[i][j].findvirus==0)
{
cout<<array[i][j].value<<"\t";
}
else
{
cout<<array[i][j].findvirus<<"\t";
}
}
cout<<"\r\n\r\n\r\n";	// 隔几行显示
}
}

void RecursiveWork(int x,int y)            // 递归
{

// 检查x,y本身是否有病毒。。。并且标记它为已访问。。当然我得首先写出是否停止退出等等的判断。。
if (array[x][y].bCheck==true||array[x][y].value==-1||array[x][y].value == 0 ) // 墙壁或者已经检查过了,或者发现没有感染则结束调用
{
return ;
}
array[x][y].bCheck=true;
if ( array[x][y].value==1 )
{
array[x][y].findvirus=2;
}

int nexti,nextj;
for (int index=1;index<9;index++)
{

nexti=x+move[index].x;
nextj=y+move[index].y;
RecursiveWork(nexti,nextj);                     // 内部调用递归
}

}
int main()
{
InitArray();
ShowInitValue();
int x,y;
cout<<"请输入起始点的x坐标的值:";
cin>>x;
cout<<"请输入起始点的y的坐标值:";
cin>>y;

RecursiveWork(x,y);                 // 外部调用递归

ShowInitValue();

return 0;
}
运行结果如下:
 






你会发现2都是连着的。其实最难的还是在于不知道把内部递归函数写在哪个位置,需要自己好好安排代码,我也不晓得怎么说。。

写完啦!!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: