数据结构中的最短路径问题,急求,在线等
小妹最近要做一个数据结构的课程设计,主题是:
旅游导游系统问题
任务:假设一个旅游景区由n个不同景点组成,并用带权临接接矩阵表示,权值表示两个景点的步行时间,试编写程序求任意两个景点的最短步行时间。
不过小妹编程能力实在有限,弄出成品惨不忍睹,但是明天就要交工了,还有n多问题没解决,望各位大侠救急。
问题有:
1. 两点之间如果没有路径,我本来设了一个错误信息“景点 到 景点之间没有路径”,但不知何故,就直接“Press any key to continue”了。
2. 任何的输入内容输入字符后就陷入无尽的死循环中,郁闷呀,我想弄成输入非数字就报错,无奈实在不会。
3. 还有我一时手误,在“请输入旅游景点个数(n>1):”后输入了0 1 2后出现了这样的画面:
呵呵,有点乱码,不好意思哦。
本来应该是重新输入景点个数的,结果直接跳过去,输入景点信息了,实在弄不懂到底是怎么回事。请求各位帮帮忙,小妹不胜感激。
不过,希望界面最好不要改动,我花了两个晚上写的文档都是以这个界面为基础的,要是要重写,就太可怕了~~~~
附上代码,对于这段代码的低能我也很惭愧,对不起教育了我这么多年的党和人民呀 ,大家将就着看吧,明天就要交作业了,实在很急,谁能帮忙,感激不尽呀~~~!!!
#include <iostream.h>
#define Num 20 //最多顶点个数
#define uplimit 100000 //定义一个无穷大的值
float Edge[Num][Num]; //Edge为带权邻接矩阵
float dist[Num]; //dist为最短路程
int path[Num]; //path为最短路径上该顶点的前一顶点的顶点号
int S[Num]; //S为已求得的在最短路径上的顶点号
int D[Num];
int n; //顶点个数
/**
* 生成地图,输入地图的基本信息
*
**/
void BuildMap(){
int i,j,s,e,contin=1;
float len;
/* 输入景点个数 */
cout<<"\t\t\t数据结构课程设计旅游导游系统"<<endl<<endl;
Loop:
cout<<"\n\t请输入旅游景点个数(n>1):";
cin>>n;
if ( n < 1 || n > Num ){
cout<<"\n\t顶点数有误,请重新输入!"<<endl;
goto Loop;
}
/* 初始化地图景点矩阵 */
for ( i = 0; i < n; i++ ){
for ( j = 0; j < n; j++ ){
Edge[i][j] = uplimit;
}
Edge[i][i] = 0;
}
cout<<"\n\t请输入各景点(景点0,1,2...)信息,以0,0,0表示结束"<<endl;
i = 1;
while ( contin == 1){
/* 输入景点之间的步行时间 */
cout<<"\n\t"<<i<<"->景点,景点,步行时间";
cin>>s>>e>>len;
/* 如果输入的格式为0,0,0 则退出步行时间的输入,转入下一步 */
if ( s == 0 && e == 0 && len == 0 ){
contin = 0;
}
/* 如果输入的景点是相同的,则重新输入 */
else if ( s == e ){
cout<<"\n\t请重新输入两不同景点!"<<endl;
}
/* 如果输入输入合法,则输入下一个景点间的步行时间 */
else if ( s >= 0 && s < n && e >= 0 && e < n && len > 0 ){
Edge[s][e] = len;
i ++;
}
/* 如果输入不合法, 则重新输入 */
else {
cout<<"\n\t\t输入内容不合规范,请重新输入!"<<endl;
}
}
}
/* 计算景点间的最短距离 */
void ShortestDist( int s){
for ( int i = 0; i < n; i ++ ){ //dist和path数组初始化
dist[i] = Edge[s][i]; //邻接矩阵第s行元素赋值到dist中
S[i] = 0; //已求出最短路径的顶点集合初始化
if ( i != s && dist[i] < uplimit ){
path[i] = s;
}
else path[i] = -1; //路径存放数组初始化
}
S[s] = 1;
dist[s] = 0; //顶点s加入顶点集合
/* 循环计算该景点与邻接景点之间的最短步行时间 */
for ( i = 0; i < n-1; i ++){ //从顶点s确定n-1条路径
float min = uplimit;
int u = s;
for ( int j = 0; j < n; j ++ ){ //选择当前不在集合S中具有最短路径的顶点u
/* 如果有路径比目前的最小值还小,则替换这个最小值 */
if ( ! S[j] && dist[j] < min ){
u = j;
min = dist[j];
}
}
S[u] = 1; //将顶点u加入集合S,表示它已在最短路径上
for ( int w = 0; w < n; w ++ ){ //修改
if ( !S[w] && Edge[u][w] < uplimit && dist[u] + Edge[u][w] < dist[w] ){
dist[w] = dist[u] + Edge[u][w];
path[w] = u;
}
}
}
}
/* 输出两个景点之间的最短步行时间,和最短路径 */
void getdata( int s,int e){
D[0] = e;
int k;
for ( k = 0; D[k] != s; k ++ ){
D[k+1] = path[D[k]];
}
if ( S[e] ){
cout<<"\t景点"<<s<<","<<e<<"之间的最短步行时间是:"<<dist[e]<<endl;
cout<<"\n\t景点"<<s<<","<<e<<"之间的最短路径是:";
for (; k != -1; k-- ){
cout<<D[k];
if ( k != 0 ){
cout<<",";
}
}
}
else
cout<<"\n\t景点"<<s<<"到景点"<<e<<"之间没有路径!"<<endl;
}
void main(){
int s,e,flag;
char option = 2;
Loop2:
BuildMap();
Loop1:
flag = 1;
while ( flag ){
cout<<"\n\t请输入起始景点号与终止景点号:";
cin>>s>>e;
cout<<endl;
if ( s < n && s >= 0 && e < n && e >= 0 ){
flag = 0;
}
else
cout<<"\n\t景点号非法,请重新输入!";
}
ShortestDist(s);
getdata(s,e);
cout<<endl
<<"\t**********************************"<<endl;
cout<<"\t\t1.计算其它景点"<<endl;
cout<<"\t\t2.建立新景点图"<<endl;
cout<<"\t\t3.结束"<<endl;
cout<<"\t**********************************"<<endl;
cout<<endl<<"\t请输入选择:";
Loop3:
cin>>option;
if ( option == 1){
goto Loop1;
}
else if ( option == 2){
goto Loop2;
}
else if (option == 3){}
else
{
cout<<"\n\t输入非法,请重新输入!"<<endl;
goto Loop3;
}
}
我有一个最短路径的写好的东西,也是在学校的时候的课程设计!
有需要的话,QQ14655611
你的代码看过了,可能要调试!不好意思,没那到多时间
BuildMap函数中
Loop:
cout<<"\n\t请输入旅游景点个数(n>1):";
cin>>n; 这里n没有声明过哦。所以导致你的第三个问题。
是啊~~
我先帮你搜索一个~~~
http://blog.csdn.net/lutexl/archive/2005/01/25/266840.aspx
http://blog.csdn.net/finytang/archive/2005/04/22/358049.aspx
现成的倒是没有~~~
帮你顶一下~~~
2. 任何的输入内容输入字符后就陷入无尽的死循环中,郁闷呀,我想弄成输入非数字就报错,无奈实在不会。
好象cin>>n;原因应该是这样的,因为如果键盘输入的是非数字字符
在你所有的输入前面加上
cin.clear();
cin.sync();
就没这样的问题了。
第一个问题死在getdata的for循环里,加个判断条件,如果走完一周还没有找到S点就结束:for ( k = 0; D[k] != s; k ++ ){
D[k+1] = path[D[k]];
}
改为:
for ( k = 0; D[k] != s && k < n; k ++ ){
D[k+1] = path[D[k]];
}
回复人: panduola918(潘多拉) ( ) 信誉:100 2005-09-08 21:20:00 得分: 0
第三个问题好解,在每个cin>>前面插入cin.getline(cp,256);就行了,注:cp为字符指针
这个我试过了,不行呢,输入“0 1 2”后再按回车键,画面没有变化呢
对不起,在第一个cin应该加在cin 后,因为如果说cin.getline之前没有任何输入他会等待输入,别的地方加在前面就行了,我试过在vc++6.0上,如果输入0 1 2就会提示"顶点输入错误,请重新输入"