前几天帮朋友写一个类孔明棋的算法,
上题      
5*5的棋盘   .表示没棋子 o表示有棋子
如:  ooooo
ooooo
oo.oo 
ooooo

ooooo
走法和孔明的走法一样
开始直接就是一个深搜    没有用数据结构 用的数组
#include<stdio.h>
#include <iostream>
#include <string.h>
using namespace std;
char data[5][5];                                //棋盘
int tag;                                       //记录棋盘上有多少个棋子
int n=0;                                       //记录方案个数
int scheme [25][4];
int code;                           //记录数据 int path(int z){                              //递归还原数据 加输出数据 if(z==0){                                  //递归结束的条件 for(int i=0;i<5;i++){for(int j=0;j<5;j++)printf("%c",data[i][j]); printf("\n");      }printf("\n"); }else{data[(scheme[z][0]+scheme[z][2])/2][(scheme[z][1]+scheme[z][3])/2]='o';data[scheme[z][0]][scheme[z][1]]='o';data[scheme[z][2]][scheme[z][3]]='.';path(z-1);                                                       //递归 上面是还原数据 下面是移动棋子 data[(scheme[z][0]+scheme[z][2])/2][(scheme[z][1]+scheme[z][3])/2]='.';data[scheme[z][0]][scheme[z][1]]='.';data[scheme[z][2]][scheme[z][3]]='o';for(int i=0;i<5;i++){for(int j=0;j<5;j++)printf("%c",data[i][j]); printf("\n");}printf("\n"); }
}int dfs(int x,int y,int z){                                        //深搜 if(tag==1) {n++;                                                      //记录可行个数 path(z-1);                                                // 初步输出棋盘 /*                                                         //方法输出 printf("方案为:");for(int i=0;i<z;i++)printf("%d.%d->%d.%d  ",scheme[i][0],scheme[i][1],scheme[i][2],scheme[i][3]);printf("\n");*/ return 1;}for(int i=0;i<5;i++){for(int j=0;j<5;j++){                       if(data[i][j]=='o')  {                                     //双重循环加判断找出棋子的位置  x=i;y=j;                                                    //判断各个方向是否可以走 if(x>=2&&data[x-1][y]=='o'&&data[x-2][y]=='.'){            //上 data[x][y]='.';                                 data[x-1][y]='.'; data[x-2][y]='o';scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x-2;  scheme[z][3]=y;tag--;code=dfs(0,0,z+1);                                                //上面的是移动位置  记录位置   减少棋子数 if(code==1)  return 1;                                        //递归到下一层 data[x][y]='o';                                      //下面的是恢复位置    增加棋子数  data[x-1][y]='o'; data[x-2][y]='.'; tag++; }if(x<=2&&data[x+1][y]=='o'&&data[x+2][y]=='.'){     //下 data[x][y]='.';data[x+1][y]='.';data[x+2][y]='o';scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x+2;  scheme[z][3]=y;tag--;code=dfs(0,0,z+1);if(code==1) return 1;data[x][y]='o';data[x+1][y]='o';data[x+2][y]='.';tag++;}if(y>=2&&data[x][y-1]=='o'&&data[x][y-2]=='.'){     //左 data[x][y]='.';data[x][y-1]='.';data[x][y-2]='o';scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x;  scheme[z][3]=y-2;tag--;if(dfs(0,0,z+1)==1) return 1;data[x][y]='o';data[x][y-1]='o';data[x][y-2]='.';tag++;}if(y<=2&&data[x][y+1]=='o'&&data[x][y+2]=='.'){     //右 data[x][y]='.';data[x][y+1]='.';data[x][y+2]='o';scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x;  scheme[z][3]=y+2;tag--;code=dfs(0,0,z+1);if(code==1) return 1;data[x][y]='o';data[x][y+1]='o';data[x][y+2]='.';tag++;}   }}}return 0; }int main(){int k=0;for(int i=0;i<5;i++){for(int j=0;j<5;j++){cin>>data[i][j];}}                                          //输入 for(int i=0;i<5;i++){for(int j=0;j<5;j++){if(data[i][j]=='o') k++;}                                       //记录初始棋子个数 }tag=k;printf("\n"); dfs(0,0,0);                                     //深搜 if(n==0) printf("无解\n"); return 0;
}
然后问题就来了   2个小时没跑出结果  简单的深度优先搜索简单的说就是穷举,所以需要减枝
后来 准备用空间换时间,加上一个标记,去掉重叠子问题
bool record[32][32][32][32][32];              //标记这用来记录不可行的子问题
后来的修正版
#include<stdio.h>
#include <iostream>
#include <time.h>
#include <string.h>
using namespace std;
char data[6][6];                                //棋盘
int tag;                                       //记录棋盘上有多少个棋子
int n=0;                                       //记录方案个数
int scheme [25][4];
int code;                                     //记录数据
bool record[32][32][32][32][32];              //标记
int sum[5]; void path(int z){                           //递归还原数据 加输出数据 if(z==0){                                  //递归结束的条件 for(int i=0;i<5;i++){for(int j=0;j<5;j++)printf("%c",data[i][j]); printf("\n");       }printf("\n"); }else{data[(scheme[z][0]+scheme[z][2])/2][(scheme[z][1]+scheme[z][3])/2]='o';data[scheme[z][0]][scheme[z][1]]='o';data[scheme[z][2]][scheme[z][3]]='.';path(z-1);                                                       //递归 上面是还原数据 下面是移动棋子 data[(scheme[z][0]+scheme[z][2])/2][(scheme[z][1]+scheme[z][3])/2]='.';data[scheme[z][0]][scheme[z][1]]='.';data[scheme[z][2]][scheme[z][3]]='o';for(int i=0;i<5;i++){for(int j=0;j<5;j++)printf("%c",data[i][j]); printf("\n");}printf("\n"); }
}int dfs(int x,int y,int z){                                        //深搜if(tag==1) {for(int i=0;i<5;i++)for(int j=0;j<5;j++){if(data[i][j]==0) data[i][j]='.';else data[i][j]='o';} n++;path(z-1);/* printf("方案为:");for(int i=0;i<z;i++)printf("%d.%d->%d.%d  ",scheme[i][0],scheme[i][1],scheme[i][2],scheme[i][3]);printf("\n");*/ return 1;}for(int i=0;i<5;i++)sum[i]=data[i][0]*16+data[i][1]*8+data[i][2]*4+data[i][3]*2+data[i][4];if(record [sum[0]][sum[1]][sum[2]][sum[3]][sum[4]]==false)  return 0;for(int i=0;i<5;i++){for(int j=0;j<5;j++){                       if(data[i][j]==1)  {                                     //双重循环加判断找出棋子的位置  x=i;y=j;                                                    //判断各个方向是否可以走 if(x>=2&&data[x-1][y]==1&&data[x-2][y]==0){            //上 data[x][y]=0;                                 data[x-1][y]=0; data[x-2][y]=1;scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x-2;  scheme[z][3]=y;tag--;code=dfs(0,0,z+1);                                                //上面的是移动位置  记录位置   减少棋子数 if(code==1)  return 1;                                        //递归到下一层 data[x][y]=1;                                      //下面的是恢复位置    增加棋子数  data[x-1][y]=1; data[x-2][y]=0; tag++; }if(x<=2&&data[x+1][y]==1&&data[x+2][y]==0){     //下 data[x][y]=0;data[x+1][y]=0;data[x+2][y]=1;scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x+2;  scheme[z][3]=y;tag--;code=dfs(0,0,z+1);if(code==1) return 1;data[x][y]=1;data[x+1][y]=1;data[x+2][y]=0;tag++;}if(y>=2&&data[x][y-1]==1&&data[x][y-2]==0){     //左 data[x][y]=0;data[x][y-1]=0;data[x][y-2]=1;scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x;  scheme[z][3]=y-2;tag--;if(dfs(0,0,z+1)==1) return 1;data[x][y]=1;data[x][y-1]=1;data[x][y-2]=0;tag++;}if(y<=2&&data[x][y+1]==1&&data[x][y+2]==0){     //右 data[x][y]=0;data[x][y+1]=0;data[x][y+2]=1;scheme[z][0]=x;  scheme[z][1]=y;  scheme[z][2]=x;  scheme[z][3]=y+2;tag--;code=dfs(0,0,z+1);if(code==1) return 1;data[x][y]=1;data[x][y+1]=1;data[x][y+2]=0;tag++;}   }}}for(int i=0;i<5;i++)sum[i]=data[i][0]*16+data[i][1]*8+data[i][2]*4+data[i][3]*2+data[i][4];record[sum[0]][sum[1]][sum[2]][sum[3]][sum[4]]=false;return 0; }int main(){int k=0;for(int i=0;i<5;i++){for(int j=0;j<5;j++)cin>>data[i][j];}//输入 for(int i=0;i<5;i++){for(int j=0;j<5;j++){if(data[i][j]=='o') {k++;data[i][j]=49-'0'; }else {data[i][j]=49-'1'; }    }                                       //记录初始棋子个数 }for(int i1=0;i1<32;i1++)                    //记录初始棋子个数 for(int i2=0;i2<32;i2++)for(int i3=0;i3<32;i3++)for(int i4=0;i4<32;i4++)for(int i5=0;i5<32;i5++){record[i1][i2][i3][i4][i5]=true;}tag=k;printf("\n"); dfs(0,0,0);                                     //深搜 if(n==0) printf("无解\n"); return 0;
}
修正版的运行时间在1S以内 
另外附上一个我看到的别人大佬写的类孔明棋算法

https://blog.csdn.net/tmljs1988/article/details/6039101

类孔明棋 c语言实验,深度优先搜索中的重叠子结果的优化问题相关推荐

  1. 南华大学计算机学院吴取劲,一种基于图深度优先搜索的基本路径集自动生成优化算法-南华大学学报.PDF...

    26 3 ( ) Vol. 26 No. 3 第 卷第 期 南华大学学报 自然科学版 2012 9 Journal of University of South China (Science and ...

  2. 深度优先搜索中的树边、后向边,前向边和交叉边

    树边:深度优先树中的边,已生成的边(如图中的实线边) 后向边:不在深度优先树中的边,但由树中的顶点指向其父顶点或者是指向顶点本身的边(图中的虚线边B) 前向边:不在深度优先树中的边,但由树中的顶点指向 ...

  3. DFS深度优先搜索中的标记问题

    同样是象棋中马的问题,有以下两个具体情景: 问题1:给起点,走三步,求所有可能到达的点 问题2:给起点,不限制步数,求能否到达终点 上边的dfs代码 void dfs(int x,int y,int ...

  4. C语言判断某个字符串中 是否存在子字符串

    直接上code char *p="add@/devices/platform/0.soc/xxx.dwmmc1/mmc_host/mmc1/mmc1";char str[128] ...

  5. 深度优先搜索(DFS) 总结(算法+剪枝+优化总结)

    深度优先搜索(DFS) 总结(算法+剪枝+优化总结) 本文中会引用部分实例.文献资料来自不同的作者之手,由于资料整理比较困难,转载地址不在文中列举.如有侵权请联系我更换或删除!对于提供题解思路的各位大 ...

  6. C++——深度优先搜索

    深度优先搜索(Depth-First Search,DFS)是一种用于遍历或搜索图或树的算法.它从起始节点开始,沿着一条路径尽可能深地探索,直到无法继续或达到目标节点,然后回溯到前一节点,继续探索其他 ...

  7. c++输出方块_C/C++编程笔记:DFS 深度优先搜索的基本思想,含实例讲解

    采用搜索算法解决问题时,需要构造一个表明状态特征和不同状态之间关系的数据结构,这种数据结构称为结点.不同的问题需要用不同的数据结构描述. 根据搜索问题所给定的条件,从一个结点出发,可以生成一个或多个新 ...

  8. 深度优先搜索知识总结

    2019独角兽企业重金招聘Python工程师标准>>> 深度优先搜索 深度优先搜索是对图的一种遍历方式,如命所示,只要有可能,就尽可能的"深入".以下为<算 ...

  9. 算法导论--广度优先搜索和深度优先搜索

    广度优先搜索 在给定图G=(V,E)和一个特定的源顶点s的情况下,广度优先搜索系统地探索G中的边,以期"发现"可从s 到达的所有顶点,并计算s 到所有这些可达顶点之间的距离(即最少 ...

最新文章

  1. penalized_tanh可视化
  2. python3.6.5安装教程-Ubuntu16.04安装python3.6.5步骤详解
  3. 【Android 插件化】Hook 插件化框架 ( 创建插件应用 | 拷贝插件 APK | 初始化插件包 | 测试插件 DEX 字节码 )
  4. Hopsan -- 液压、电力等行业的仿真开源软件
  5. 【NOIP必备攻略】 基本noilinux使用方法
  6. ASP.Net Core Razor 部署AdminLTE框架
  7. php内置的数组函数大全,php数组的内置函数大全
  8. 一个figure存在多个legend:多行多列图例
  9. 二十五、JAVA多线程(六、线程控制操作)
  10. 图像处理基础:特征金字塔
  11. 10月24日——程序猿的节日
  12. 2022-4-12作业
  13. MySQL基本增删改查以及搭配node在项目中的操作
  14. 游戏开发 unity3d python_游戏研发系列 Unity3D/2D游戏开发从0到1 第2版.pdf
  15. 用Python制作动态二维码,一行代码就做到了
  16. abb机器人负载配置设定_ABB机器人配置Profinet网络配置流程.pdf
  17. 排序算法图解(四):希尔排序
  18. 2020年第十届亚太地区大学生数学建模
  19. Mycat分库分表分片方式
  20. 办公技巧 使用插件提取word中的连续页

热门文章

  1. 异地远程访问本地SQL Server数据库【无公网IP内网穿透】
  2. java后端判断接收的日期范围不能超出一周
  3. 基于ENVI/IDL 的一键化实现LST-NDVI的干湿边方程拟合,并得到TVDI计算结果图
  4. Lyapunov-Krasovskii泛函二重积分项求导_原理
  5. 基于大数据技术的园区安全环保一体化综合管理系统的应用
  6. 全国大学生数学建模大赛 B 题解题思路
  7. 基于单片机开发的快速体温计方案
  8. 高质量免费PPT模板下载网站-朴尔PPT - 知乎
  9. Log4js原理解析
  10. 软考高级-系统架构师-案例分析-架构设计