农夫过河-广度策略 pta
一个农夫带着一只狼、一只羊和一棵白菜,身处河的南岸。他要把这些东西全部运到北岸。遗憾的是他只有一只小船,小船只能容下他和一件物品。这里只能是农夫来撑船。同时因为狼吃羊,而羊吃白菜,所以农夫不能留下羊和狼或者羊和白菜单独在河的一边,自己离开。好在狼属于肉食动物,不吃白菜。农夫怎样才能把所有的东西安全运过河呢?
为了表示每个物品的位置,采用二进制位来区分南岸和北岸,0表示在南岸,1表示在北岸。用四个二进制位XXXX分别表示农夫、狼、菜和羊四个物品所在的位置。例如1110表示农夫、狼和菜在北岸,菜在南岸。农夫过河问题的初始状态为0000,结束状态为1111。
输入格式:
无输入
输出格式:
输出农夫移动物品的中间状态的逆序
输入样例:
输出样例:
15 6 14 2 11 1 9 0
代码
#include <stdio.h>
#include <stdlib.h>
typedef int DataType;
struct Queue
{int Max;int f;int r;DataType *elem;
};
typedef struct Queue *SeqQueue;SeqQueue SetNullQueue_seq(int m)
{SeqQueue squeue;squeue = (SeqQueue)malloc(sizeof(struct Queue));if (squeue == NULL){printf("Alloc failure\n");return NULL;}squeue->elem = (int *)malloc(sizeof(DataType) * m);if (squeue->elem != NULL){squeue->Max = m;squeue->f = 0;squeue->r = 0;return squeue;}
}int IsNullQueue_seq(SeqQueue squeue)
{return (squeue->f == squeue->r);
}
void EnQueue_seq(SeqQueue squeue, DataType x)
{if ((squeue->r + 1) % squeue->Max == squeue->f)printf("It is FULL Queue!");else{squeue->elem[squeue->r] = x;squeue->r = (squeue->r + 1) % squeue->Max;}
}
void DeQueue_seq(SeqQueue squeue)
{if (IsNullQueue_seq(squeue) == 1)printf("it is empty queue!");else{squeue->f = (squeue->f + 1) % (squeue->Max);}
}
DataType FrontQueue_seq(SeqQueue squeue)
{if (IsNullQueue_seq(squeue) == 1){printf("It is empty queue");return 33;}else{return squeue->elem[squeue->f];}
}
//***************************************
int FarmerOnRight(int status) //判断当前条件下农夫的位置
{return (0 != (status & 0x08));
}
int WorfOnRight(int status) //判断当前位置下狼的位置
{return (0 != (status & 0x04));
}
int CabbageOnRight(int status) //判断当前位置下白菜的位置
{return (0 != (status & 0x02));
}
int GoatOnRight(int status) //判断当前位置下羊是否在南岸
{return (0 != (status & 0x01));
}
int IsSafe(int status) //判断当前位置下羊是否安全
{if ((GoatOnRight(status) == CabbageOnRight(status)) && (GoatOnRight(status) != FarmerOnRight(status)))return 0; //羊吃白菜if ((GoatOnRight(status) == WorfOnRight(status)) && (GoatOnRight(status) != FarmerOnRight(status)))return 0; //狼吃羊return 1; //其他状态时安全的
}
void FarmerRiver()
{int i, movers, nowstatus, newstatus;int status[16]; //用于记录已考虑的状态路径SeqQueue moveTo; //用于记录可以安全到达的中间状态moveTo = SetNullQueue_seq(20); //创建空队列EnQueue_seq(moveTo, 0x00); //初始状态时所有物品在南岸for (i = 0; i < 16; i++) //数组status初始化位-1status[i] = -1;status[0] = 0;while (!IsNullQueue_seq(moveTo) && (status[15] == -1))//队列非空且没有到达结束状态{nowstatus = FrontQueue_seq(moveTo); //取队头状态为当前状态DeQueue_seq(moveTo);for (movers = 1; movers <= 8; movers <<= 1) //遍历三个要移动的物品//考虑各种物品移动if ((0 != (nowstatus & 0x08)) == (0 != (nowstatus & movers)))//考虑农夫与移动的物品在同一侧{newstatus = nowstatus ^ (0x08 | movers); //计算新状态//如果新状态时安全的且之前没有出现过if (IsSafe(newstatus) && (status[newstatus] == -1)){status[newstatus] = nowstatus; //记录新状态EnQueue_seq(moveTo, newstatus); //新状态入队}}}//输出经过的装态路径if (status[15] != -1) //到达最终状态{// printf("the reverse path is:\n");for (nowstatus = 15; nowstatus >= 0; nowstatus = status[nowstatus]){// printf("The nowstatus is:%d\n", nowstatus);printf("%d ", nowstatus);if (nowstatus == 0)return;}}elseprintf("No solution.\n"); //问题无解
}
int main()
{FarmerRiver();return 0;
}
农夫过河-广度策略 pta相关推荐
- 迷宫-广度策略 pta
一个陷入迷宫的老鼠如何找到出口的问题.老鼠希望系统性地尝试所有的路径之后走出迷宫.如果它到达一个死胡同,将原路返回到上一个位置,尝试新的路径.在每个位置上老鼠可以向八个方向运动,顺序是从正东开始按照顺 ...
- 用BFS(广度优先搜索queuelist)算法解决农夫过河问题
用BFS(广度优先搜索queue&&list)算法解决农夫过河问题 一.问题需求分析 一个农夫带着一只狼.一只羊和一棵白菜,身处河的南岸.他要把这些东西全部运到北岸.问题是他面前只有一 ...
- 农夫过河问题的c语言实现
文章来源:http://blog.csdn.net/neweastsun/archive/2009/11/08/4785611.aspx 一. 问题需求分析 一个农夫带着一只狼.一只羊和 ...
- java农夫过河问题_农夫过河问题——C语言程序设计(转)
一个农夫带着一只狼.一只羊和一棵白菜,身处河的南岸.他要把这些东西全部运到北岸.问题是他面前只有一条小船,船小到 只能容下他和一件物品,另外只有农夫能撑船.另外,因为狼能吃羊,而羊爱吃白菜,所以农夫不 ...
- C语言位运算农夫过河,位运算常见操作和农夫过河问题(C++实现)
二进制常见操作 二进制数中 1 的个数 解法 1 用 n & 1 判断最右边一位是否为 1,右移之后继续判断最右边一位,重复直到 n = 0.时间复杂度为 O(log2n) #include ...
- 算法系列之十四:狼、羊、菜和农夫过河问题
算法系列之十四:狼.羊.菜和农夫过河问题 题目描述:农夫需要把狼.羊.菜和自己运到河对岸去,只有农夫能够划船,而且船比较小,除农夫之外每次只能运一种东西,还有一个棘手问题,就是如果没有农夫看着,羊会偷 ...
- 农夫过河问题——程序设计
农夫过河问题--程序设计 一.问题需求分析 一个农夫带着一只狼.一只羊和一棵白菜,身处河的南岸.他要把这些东西全部运到北岸.问题是他面前只有一条小船,船小到只能容下他和一件物品,另外只有农夫能撑船.另 ...
- C++:农夫过河问题
农夫.羊.菜和狼的故事 题目描述 有一个农夫带一只羊.一筐菜和一只狼过河.如果没有农夫看管,则狼要吃羊,羊要吃菜.但是船很小,只够农夫带一样东西过河.问农夫该如何解此难题? 输入描述: 题目没有任何输 ...
- c语言农夫过河游戏代码解释,农夫过河C++代码
农夫过河C++代码 ///农夫过河C++代码 /// 作者:lyb661 时间:2015年8月 /* 农夫过河问题思路:主要使用用容器,一个存储此岸,一个存储彼岸,一个存储结果(用于打印). 过 ...
最新文章
- 神经网络的可解释性综述!
- 新版IntelliJ IDEA Web项目配置完整流程
- Python中数据类型的操作
- python字符串添加_python字符串的增删改查
- mysql交叉编译 cmake_CMake交叉编译配置
- 计算机专业学的东西其实很少,为什么计算机专业的学生要学习使用Linux系统?...
- python判断文件或文件夹是否存在
- C#-SpecialFolder-特殊路径获取
- 海康摄像头近距离不能对焦模糊问题
- PDF虚拟打印机怎么虚拟打印
- 程序员面试华为,面试官出了这样一个面试题,网友:题目太难了
- si4745 FM-AM-SW 音量控制芯片 驱动详解
- 武汉市公积金提取流程
- 实战:淘宝新品想抢占市场流量 分三步进行
- Linux下获取Root权限的方法
- 成都Uber优步司机奖励政策(3月4日)
- 手机没网了,却还能支付,这是什么原理?
- CTF Crypto---RSA NC不互素
- 视频直播的 推流是啥意思
- sipdroid软件直接使用andriod打网络电话
热门文章
- phpstudy安装后使原本的mysql连接不上
- 佳能MG2580S打印机进纸不顺畅维修
- 《利用python进行数据分析》读书笔记--第九章 数据聚合与分组运算(一)
- 《深入浅出人工智能(第2版)》之“什么是人工智能?”
- flex datagrid组件中添加别的组件
- matlab、python打字变红,格式错误问题
- 北京师范大学计算机考研难嘛,北京师范大学考研难吗?一般要什么水平才可以进入?...
- 密室鼻祖 深红色房间超详细攻略
- arcgis图斑尖角检查_ArcGIS消除零碎图斑(Eliminate)
- 如何建立高质量团队-《克服团队协作的五种障碍》笔记与心得