8数码问题的宽度优先搜索策略实现.

#include<stdio.h>
#include<conio.h>

typedef struct Node
{
char state[9];/*存储矩阵*/
int  father;/*指向产生自身的父结点的下标*/
char flag;/*访问标记*/
}Node;
char target[9]={'0','1','2','3','4','5','6','7','8'};
Node buff[5000];
int index=0;/*Node节点的浮标指向可用节点*/
int current=0;/*指向Node接点的分界线(前部分是访问过的)*/
int match(int j) /*是否是目标*/
{
    int i=0;
    while(buff[j].state[i]==target[i]&&i<9)i++;
    if(i==9) return 0;
    else return 1;
}
void addNode(Node nd)/*添加节点到队列*/
{
    int i=0;
    while(i<9)
    {
        buff[index].state[i]=nd.state[i];
        i++;
    }
    buff[index].father=nd.father;
    buff[index].flag=nd.flag;
    index++;
}
Node initAll()/*初始化*/
{
    Node nd;
    int i;
    printf("输入初始状态;\n");
    for(i=0;i<9;i++)
    {
        scanf("%s",&nd.state[i]);
        /*nd.state[i]=getch();*/
    }
    nd.father=-1;
    nd.flag='n';
    index=0;
    current=0;
    return nd;
}
void visitNode(int i)/*访问节点i*/
{
    buff[i].flag='y';
}
int search(int i)/*查询节点i的空格位置*/
{
    int j=0;
    while(buff[i].state[j]!='0'&&j<9)j++;
    return j;
}
Node sonNode(int i,char c) /*对节点i进行扩展*/
{
    int j;
    char ch[9];
    char tc;
    Node nd;
    for(j=0;j<9;j++)nd.state[j]=buff[i].state[j];
    j=search(i);
    if(c=='l')
    {
       if(j%3==0) nd.flag='0';
       else
       {
        tc=nd.state[j];
        nd.state[j]=nd.state[j-1];
        nd.state[j-1]=tc;
        nd.flag='n';
        }
    }
    if(c=='d')
    {
        if(j>5) nd.flag='0';
        else
        {
            tc=nd.state[j];
            nd.state[j]=nd.state[j+3];
            nd.state[j+3]=tc;
            nd.flag='n';
        }
    }
    if(c=='r')
    {
        if(j%3==2) nd.flag='0';
        else
        {
            tc=nd.state[j];
            nd.state[j]=nd.state[j+1];
            nd.state[j+1]=tc;
            nd.flag='n';
        }
    }
    if(c=='u')
    {
        if(j<3) nd.flag='0';
        else
        {
            tc=nd.state[j];
            nd.state[j]=nd.state[j-3];
            nd.state[j-3]=tc;
            nd.flag='n';
        }
    }
    nd.father=i;
    return nd;
}
int lookBack(Node nd) /*检查节点是否已经访问过*/
{
    int i;
    int j=0;
    for(i=0;i<current&&j<9;i++)
    {
        j=0;
        while(nd.state[j]==buff[i].state[j]&&j<9)j++;
    }
    if(j==9) return i;
    else return 0;
}
void show(int i)
{
    int j;
    for(j=0;j<9;j++)
    printf("%c ",buff[i].state[j]);
    printf("\n");
}
void showPath(int i)
{
    printf("The process is:\n");
    while(buff[i].father!=-1)
    {
        show(i);
        i=buff[i].father;
    }
}

void main()
{
    char ch='y';
    Node currentNode;
    while(ch=='y')
    {
        currentNode=initAll();
        addNode(currentNode);
        while(current<index&&match(current)!=0)
        {
            visitNode(current);
            currentNode=sonNode(current,'l'); /*左扩展*/
            if(currentNode.flag!='0'&&lookBack(currentNode)==0) addNode(currentNode);
            currentNode=sonNode(current,'d'); /*下扩展*/
            if(currentNode.flag!='0'&&lookBack(currentNode)==0) addNode(currentNode);
            currentNode=sonNode(current,'r'); /*右扩展*/
            if(currentNode.flag!='0'&&lookBack(currentNode)==0) addNode(currentNode);
            currentNode=sonNode(current,'u'); /*上扩展*/
            if(currentNode.flag!='0'&&lookBack(currentNode)==0) addNode(currentNode);
            current++;
        }
        if(current<index)
        {
            showPath(current);
            printf("找到");
        }
        else printf("失败");
        printf("\n");
        printf("Do you want to end this program?(y/n)");
        scanf("%c",&ch);
    }
}

posted on 2006-10-31 19:04  空空色色  阅读(546)  评论(0编辑  收藏  举报