返回信息流#include<stdio.h>
#include<stdlib.h>
#define SIZE 20//max.rows
#define MAXSTEPS (SIZE*SIZE)//max.steps
struct point{short r;short c;};
char **maze;
struct point *path,*bestpath;
int rows,cols,sp=MAXSTEPS;//rows/cols that user inputs,shortestPath
int x[4]={0,1,0,-1},y[4]={-1,0,1,0};//Left,Down,Right,Up
//check if the position is reasonable
int LegalPos(int r,int c) {
if ((r<0)||(c<0)||(r>rows-1)||(c>cols-1)) return 0;
return 1;
}
//visit the maze from the point(r,c) at step.
void Visit(int step,int r,int c) {
int d,i;//direction
int newr,newc;//newrow,newcol
for (d=0;d<4;d++){//four directions to move
newr=r+x[d];
newc=c+y[d];
if (LegalPos(newr,newc)&&('#'!=*(*(maze+newr)+newc))){//check if we can move to (newr,newc)
path[step].r=newr;//record the point in path.
path[step].c=newc;
if ('E'==*(*(maze+newr)+newc)){//check if we reach the end
if (step<sp){//if find shorter path
sp=step;
for (i=0;i<=step;i++){//copy the path to bestpath
bestpath[i].r=path[i].r;
bestpath[i].c=path[i].c;
}
}
}
if ('.'==*(*(maze+newr)+newc)){//if we can pass the point
*(*(maze+newr)+newc)='V';//mark the point as Visited
Visit(step+1,newr,newc);//continue visit the maze
*(*(maze+newr)+newc)='.';//backtrace:remark it
path[step].r=SIZE;//reset the path at step
path[step].c=SIZE;
}
}
}
}
int main()
{
int r,c,found=0,i;
printf("Please input the row and column of the maze(<=20):");
scanf("%d %d",&rows,&cols);
if ((rows<0)||(cols<0)||(rows>SIZE-1)||(cols>SIZE-1)){
printf("error input\n");
return -1;
}
maze=(char **)malloc(sizeof(char *)*rows);
if (!maze){
printf("error while malloc maze\n");
return -1;
}
for(i=0;i<rows;i++){
maze[i]=(char*)malloc(sizeof(char)*(cols));
if (!maze[i]){
printf("error while malloc maze\n");
return -1;
}
}
path=(struct point *)malloc(sizeof(struct point)*rows*cols);
if (!path){
printf("error while malloc path\n");
return -1;
}
bestpath=(struct point *)malloc(sizeof(struct point)*rows*cols);
if (!bestpath){
printf("error while malloc bestpath\n");
return -1;
}
printf("Please input the strings:\n");
fflush(stdin);
for(r=0;r<rows;r++) {
fgets(*(maze+r),cols+2,stdin);
}
//find out the point which we start from
for(r=0;r<rows;r++){
for(c=0;c<cols;c++){
if('S'==*(*(maze+r)+c)){
found=1;break;
}
}
if (found) break;
}
//record it in path
path[0].r=r;path[0].c=c;
//visit the maze from START point.
Visit(1,r,c);
//print the bestpath info.
for(i=0;i<=sp;i++)
printf("(%d,%d)\n",bestpath[i].r+1,bestpath[i].c+1);
system("pause");
return 0;
}
该程序是上课老师给我们讲的找迷宫程序,楼主是大一,希望学长学姐帮忙解决一下!
上面两处蓝色的地方,我非常一会malloc申请空间的时候(char *)以rows个空间,因为fgets函数用时必须多读入两个字符\n \0但是空间只有那么点 多读入的去哪了?没存吗? 当我把fgets函数中+2去掉后 这个程序就不行了 显示的很奇怪的看不懂 这是为什么呢 多读入的没存 为何又起了该起的作用呢
这是一条镜像帖。来源:北邮人论坛 / cpp / #85055同步于 2015/1/7
该镜像源已超过 30 天没有更新,可能在源站已被删除。
CPP机器人发帖
问一个关于malloc函数和fgets的问题
yu1336199790
2015/1/7镜像同步5 回复
订阅后,新回复会通过你的通知中心匿名送达。
5 条回复
该程序是上课老师给我们讲的找迷宫程序,楼主是大一,希望学长学姐帮忙解决一下!
上面两处蓝色的地方,我非常不懂 malloc申请空间的时候(char *)乘rows 个空间,因为fgets函数用时必须多读入两个字符\n \0但是空间只有那么点 多读入的去哪了?没存吗? 当我把fgets函数中+2去掉后 这个程序就不行了 显示的很奇怪的看不懂 这是为什么呢 多读入的没存 为何又起了该起的作用呢
关键在这两个地方:maze=(char **)malloc(sizeof(char *)*rows);
maze[i]=(char*)malloc(sizeof(char)*(cols));
指针的指针分配空间,类似理解为二维数组。另外不知道你说的什么,就晃眼啦。
不要搞大字报啊
你应该标的是maze[i]=(char*)malloc(sizeof(char)*(cols));和 fgets(*(maze+r),cols+2,stdin);
在你老老实实输入col个字符的情况下,这里fgets读入了cols+1个字符,其中前col个字符是你输入的字符,第col+1个是换行符,第col+2个是fgets函数自动加上的'\0'
假设col是4,那么你为*(maze+r)也就是maze[i]申请的内存就是Addr,Addr+1,Addr+2,Addr+3。
而你通过fgets函数读的字符串就放到Addr,Addr+1,Addr+2,Addr+3,Addr+4,Addr+5的内存上了
明白了吗?也就是内存越界访问了,专业点儿的说法就是缓冲区溢出了。
你可以试验一下把maze[i]=(char*)malloc(sizeof(char)*(cols));改成maze[i]=(char*)malloc(sizeof(char));
这程序看上去也能正常运行,但它是有安全隐患的
【 在 succubus 的大作中提到: 】
: 不要搞大字报啊
: 你应该标的是maze[i]=(char*)malloc(sizeof(char)*(cols));和 fgets(*(maze+r),cols+2,stdin);
: 在你老老实实输入col个字符的情况下,这里fgets读入了cols+1个字符,其中前col个字符是你输入的字符,第col+1个是换行符,第col+2个是fgets函数自动加上的'\0'
: ...................
就是说读入的最后是被存到了不知道的区域 ?