资源描述
校园导航
课程设计报告书
专 业:计算机科学与技术
课程设计名称:《数据结构课程设计》
题 目:校园导航问题
班 级:
学 号:
姓 名:
同 组 人 员:
指 导 老 师:
完 成 时 间:2012年2月17日
摘要
校园导航问题是基于校园中的不同的景点,从陌生人的角度,为来往的客人提供校园景点相关信息的查询以及为来往的客人提供校园中任意景点的问路查询,以便客人能用最短的时间从某一地点到达想要去的地方。大大节约了旅客参观校园的时间。
本文是采用C++作为开发语言,又最大程度上用了C语言的有关的语法。以visual c++6.0为开发工具。旨在实现校园导航系统中,学校的简介,景点的介绍,路线查询等基本的问题。为来往客人参观校园提供方便。
关键词:C++;C;visual c++6.0;校园导航
目录
目录 1
第一章 开发环境和开发工具 1
1.1 C/ C ++语言简介 1
1.2 开发背景 1
1.3 开发环境 1
第二章 算法思想 2
2.1 系统需求分析 2
2.2 系统总体设计 3
2.2.1 系统设计目标 3
2.2.2 开发设计思想 3
2.2.3 系统功能模块设计 3
2.3 算法思想描述 4
第三章 算法实现 6
3.1 数据结构 6
3.2 程序模块 6
3.3 各模块之间的调用关系上 12
3.4 源程序代码 12
第四章 测试与分析 22
4.1 测试数据选择 22
4.2 测试结果分析 26
总 结 27
心得体会 28
参考文献 29
第一章 开发环境和开发工具
1.1 C/ C ++语言简介
C语言是一种计算机程序设计语言。它既具有高级语言的特点,又具有汇编语言的特点。它由美国贝尔研究所的D.M.Ritchie于1972年推出。1978后,C语言已先后被移植到大、中、小及微型机上。它可以作为工作系统设计语言,编写系统应用程序,也可以作为应用程序设计语言,编写不依赖计算机硬件的应用程序。它的应用范围广泛,具备很强的数据处理能力,不仅仅是在软件开发上,而且各类科研都需要用到C语言,适于编写系统软件,三维,二维图形和动画。具体应用比如单片机以及嵌入式系统开发。
C++是一种静态数据类型检查的、支持多重编程范式的通用程序设计语言。它支持过程化程序设计、数据抽象、面向对象程序设计、制作图标等等泛型程序设计等多种程序设计风格。
1.2 开发背景
随着科学技术的不断发展,计算机科学日渐成熟,其强大的功能已为人们所深刻认识,它己进入人类社会的各个领域并发挥着越来越重要的作用。采用计算机进行校园导航已成为衡量校园数字化的重要标志。校园导航效率的好坏对于来校参观的客人和学校管理者来说都至关重要,在很大程度上影响着校园的数字化建设和学校的影响力。因此,本文所研究的校园导航系统具有一定的使用价值和现实意义。
1.3 开发环境
本文所采用的开发环境主要是基于c++的visual stadio c++。它是一个系统的集成开发环境。很适合C\C++程序的开发。我们日常的学习和生活中大多就用这个开发环境进行学习和编程。
第二章 算法思想
2.1 系统需求分析
1、设计你的学校的校园平面图,所选的景点不少于10个。以图中顶点表示校内各景点,存放景点名称、代号、简介等信息;以边表示路径,存放路径长度等相关信息。
2、为来往客人提供图中任意景点相关信息的查询。
3、为来往的客人提供图中任意景点的问路查询,即查询任意两个景点间的一条最短的简单路径。
根据以上分析和抽象可得到本系统的抽象数据类型如下:
ADT graph{
数据对象 R:V是校园中景点的集合,称为顶点集。
R={VR}
VR={<v,w,>|v,w∈V且P(v,w),(v,w)表示从景点v到景点w的路径长度
基本操作 P:
Creatgraph(&G,V,VR)
初始条件:V是图的顶点集,VR是图中边的集合。
操作结果:按V和VR的定义构造图G。
Output(G)
初始条件:图G已经存在。
操作结果:打印出图的信息
ShortestPath(G,v)
初始条件:图G已存在,v是图中的一个顶点。
操作结果:返回从v出发到图中任意顶点的最短的路径。
}ADT graph;
2.2 系统总体设计
2.2.1 系统设计目标
本文研究开发的校园导航系统用于支持来往校园参观的客人提供最省时的导航服务,有如下三个方面的目标:
1、为来往的客人提供校园的简介。
2、为来往的客人提供校园中各景点的简介,以及各景点的距离等情况。
3、为来往的客人提供到达目的地的最短的路线。
2.2.2 开发设计思想
基于以上系统设计目标,本文在开发校园导航系统时遵循了以下开发设计思想:
1、采用现有的软硬件环境及先进的管理系统开发方案,从而达到充分利用现有资源,提高系统开发水平和应用效果的目的。
2、尽量达到操作过程中的直观、方便、实用、安全等要求。
3、系统采用模块化程序设计方法,既便于系统功能的各种组合和修改,又便于未参与开发的技术维护人员补充、维护。
2.2.3 系统功能模块设计
本系统分为四个模块:菜单模块、景点介绍模块、路径查询模块、最短路径模块。得到如图3-1所示的系统功能模块图。
主菜单
校园导航系统
菜单
景点介绍
路径查询
最短路径
查询子菜单
退
出
学校简介
景点简介
各景点间距离
最短路径长度
最短路线
图3-1系统功能模块图
2.3 算法思想描述
1、迪杰斯特拉算法思想:
按路径长度递增次序产生最短路径算法:
把V分成两组:
(1)S:已求出最短路径的顶点的集合
(2)V-S=T:尚未确定最短路径的顶点集合
将T中顶点按最短路径递增的次序加入到S中,
保证:(1)从源点V0到S中各顶点的最短路径长度都不大于
从V0到T中任何顶点的最短路径长度
(2)每个顶点对应一个距离值
S中顶点:从V0到此顶点的最短路径长度
T中顶点:从V0到此顶点的只包括S中顶点作中间
顶点的最短路径长度
依据:可以证明V0到T中顶点Vk的最短路径,或是从V0到Vk的
直接路径的权值;或是从V0经S中顶点到Vk的路径权值之和
2、邻接矩阵建立有无向权图的算法思想:
用两个数组分别存储数据元素的信息和数据之间的关系的信息其形式描述如下:
#define Max 32767//最大值∞
#define NUM 11//最大顶点个数
typedef struct ArcCell{
int adj; // 相邻接的景点之间的路程
char *info;
}ArcCell; // 定义边的类型
typedef struct VertexType{
int number; // 景点编号
char *sight; // 景点名称
char *description; // 景点描述
}VertexType; // 定义顶点的类型
typedef struct{
VertexType vex[NUM]; // 图中的顶点,即为景点
ArcCell arcs[NUM][NUM]; // 图中的边,即为景点间的距离
int vexnum,arcnum; // 顶点数,边数
}MGraph; // 定义图的类型
其中用二维数组表示途中个边之间的关系。
第三章 算法实现
3.1 数据结构
1、顶点、边和图类型:
typedef struct ArcCell{
int adj; // 相邻接的景点之间的路程
char *info;
}ArcCell; // 定义边的类型
typedef struct VertexType{
int number; // 景点编号
char *sight; // 景点名称
char *description; // 景点描述
}VertexType; // 定义顶点的类型
typedef struct{
VertexType vex[NUM]; // 图中的顶点,即为景点
ArcCell arcs[NUM][NUM]; // 图中的边,即为景点间的距离
int vexnum,arcnum; // 顶点数,边数
}MGraph; // 定义图的类型
3.2 程序模块
1.main函数
void main() // 主函数
{ int v0,v1;
char ck;
system("color cb");
CreateUDN(NUM,11);
do
{
ck=Menu();
switch(ck)
{
case'1':
introduce();
printf("\n\n\t\t\t%-25s\n\n",G.vex[0].description);
getchar();
getchar();
break;
case '2':
system("cls");
pingmu();
printf("\n\n\t\t\t请选择起点景点(1~10):");
scanf("%d",&v0);
printf("\t\t\t请选择终点景点(1~10):");
scanf("%d",&v1);
ShortestPath(v0); // 计算两个景点之间的最短路径
output(v0,v1); // 输出结果
printf("\n\n\t\t\t\t请按回车键继续...\n");
getchar();
getchar();
break;
case '3':search();
break;
case'5':
PrintMGraph();
printf("\n\n\t\t\t\t请按回车键继续...\n");
getchar();
getchar();
break;
};
}while(ck!='e');
}
2.主菜单
char Menu() // 主菜单 //
{
char c;
int flag;
do{
flag=1;
system("cls");
pingmu();
printf("\n\t\t┏━━━━━━━━━━━━━━━━━━━┑\n");
printf("\t\t┃ ┃\n");
printf("\t\t┃ 1.学校简介 ┃\n");
printf("\t\t┃ 2.查询景点路径 ┃\n");
printf("\t\t┃ 3.查询景点信息 ┃\n");
printf("\t\t┃ 5.查询各景点之间的距离 ┃\n");
printf("\t\t┃ e.退出 ┃\n");
printf("\t\t┃ ┃\n");
printf("\t\t┗━━━━━━━━━━━━━━━━━━━┛\n");
printf("\t\t\t\t请输入您的选择:");
scanf("%c",&c);
if(c=='1'||c=='2'||c=='3'||c=='5'||c=='e')
flag=0;
}while(flag);
return c;
}
3.查询子菜单
char SearchMenu() // 查询子菜单
{
char c;
int flag;
do{
flag=1;
system("cls");
pingmu();
printf("\n\t\t┏━━━━━━━━━━━━━━━━━━┑\n");
printf("\t\t┃ ┃\n");
printf("\t\t┃ 1、按照景点编号查询 ┃\n");
printf("\t\t┃ 2、按照景点名称查询 ┃\n");
printf("\t\t┃ e、返回 ┃\n");
printf("\t\t┃ ┃\n");
printf("\t\t┗━━━━━━━━━━━━━━━━━━┛\n");
printf("\t\t\t请输入您的选择:");
scanf("%c",&c);
if(c=='1'||c=='2'||c=='e')
flag=0;
}while(flag);
return c;
}
4.查询景点信息
void search() // 查询景点信息
{
int num;
int i;
char c;
char name[20];
do
{
system("cls");
c=SearchMenu();
switch (c)
{
case '1':
system("cls");
//introduce();
pingmu();
printf("\n\n\t\t请输入您要查找的景点编号:");
scanf("%d",&num);
for(i=0;i<NUM;i++)
{
if(num==G.vex[i].number)
{
printf("\n\n\t\t\t您要查找景点信息如下:");
printf("\n\n\t\t\t%-25s\n\n",G.vex[i].description);
printf("\n\t\t\t按任回车返回...");
getchar();
getchar();
break;
}
}
if(i==NUM)
{
printf("\n\n\t\t\t没有找到!");
printf("\n\n\t\t\t按回车键返回...");
getchar();
getchar();
}
break;
case '2':
system("cls");
pingmu();
introduce();
printf("\n\n\t\t请输入您要查找的景点名称:");
scanf("%s",name);
for(i=1;i<NUM;i++)
{
if(!strcmp(name,
G.vex[i].sight))
{
printf("\n\n\t\t\t您要查找景点信息如下:");
printf("\n\n\t\t\t%-25s\n\n",G.vex[i].description);
printf("\n\t\t\t按回车键返回...");
getchar();
getchar();
break;
}
}
if(i==NUM)
{
printf("\n\n\t\t\t没有找到!");
printf("\n\n\t\t\t按回车键返回...");
getchar();
getchar();
}
break;
}
}while(c!='e');
}
5.创建图的函数
void CreateUDN(int v,int a) // 创建图的函数
6. 打印出邻接矩阵
void PrintMGraph()
{
int i,j;
cout<<"\n ====================================================================\n\n ";
for(i=1;i<G.vexnum;++i)
{
cout<<G.vex[i].sight<<" ";
}
cout<<endl;
for(i=1;i<G.vexnum;++i)
{
cout<<"\n\n"<<G.vex[i].sight<<" ";
for(j=1;j<G.vexnum;++j)
{
if(G.arcs[i][j].adj==Max)
cout<<" no ";
else
cout<<" "<<G.arcs[i][j].adj;
}
}
cout<<"\n\n\n\n==========================================================================================\n\n\n";
7.迪杰斯特拉算法
void ShortestPath(int num) // 迪杰斯特拉算法最短路径函数 num为入口点的编号
{
int v,w,i,t; // i、w和v为计数变量
int final[NUM];
int min;
for(v=1;v<NUM;v++)
{
final[v]=0; // 假设从顶点num到顶点v没有最短路径
D[v]=G.arcs[num][v].adj;// 将与之相关的权值放入D中存放
for(w=1;w<NUM;w++) // 设置为空路径
P[v][w]=0;
if(D[v]<32767) // 存在路径
{
P[v][num]=1; // 存在标志置为一
P[v][v]=1; // 自身到自身
}
}
D[num]=0;
final[num]=1; // 初始化num顶点属于S集合
// 开始主循环,每一次求得num到某个顶点的最短路径,并将其加入到S集合
for(i=1;i<NUM;++i) // 其余G.vexnum-1个顶点
{
min=Max; // 当前所知离顶点num的最近距离
for(w=1;w<NUM;++w)
if(!final[w]) // w顶点在v-s中
if(D[w]<min) // w顶点离num顶点更近
{
v=w;
min=D[w];
}
final[v]=1; // 离num顶点更近的v加入到s集合
for(w=1;w<NUM;++w) // 更新当前最短路径极其距离
if(!final[w]&&((min+G.arcs[v][w].adj)<D[w]))// 不在s集合,并且比以前所找到的路径都短就更新当前路径 //
{
D[w]=min+G.arcs[v][w].adj;
for(t=0;t<NUM;t++)
P[w][t]=P[v][t];
P[w][w]=1;
}
}
}
8、输出:
屏幕输出函数:void pingmu();
最短路线输出函数void output;
3.3 各模块之间的调用关系上
模块调用关系如图3—2所示:
main
CreateUDN
menu
search
ShortestPath
output
PrintMGraph
pingmu
searchmenu
图3—2模块调用关系图
3.4 源程序代码
#include<iostream.h>
#include "string.h"
#include "stdio.h"
#include "stdlib.h"
#define Max 32767
#define NUM 11
typedef struct ArcCell{
int adj; // 相邻接的景点之间的路程
char *info;
}ArcCell; // 定义边的类型
typedef struct VertexType{
int number; // 景点编号
char *sight; // 景点名称
char *description; // 景点描述
}VertexType; // 定义顶点的类型
typedef struct{
VertexType vex[NUM]; // 图中的顶点,即为景点
ArcCell arcs[NUM][NUM]; // 图中的边,即为景点间的距离
int vexnum,arcnum; // 顶点数,边数
}MGraph; // 定义图的类型
MGraph G; // 把图定义为全局变量
int P[NUM][NUM]; // //
long int D[NUM]; // 辅助变量存储最短路径长度
int x[13]={0};
void CreateUDN(int v,int a); // 创建图的函数
void pingmu(); //屏幕输出函数
void introduce();
void ShortestPath(int num); //最短路径函数
void output(int sight1,int sight2); //输出函数
void PrintMGraph();
char Menu(); // 主菜单
void search();
;// 查询景点信息
char SearchMenu(); // 查询子菜单
void NextValue(int);
void display(); // 显示遍历结果
void main() // 主函数
{
int v0,v1;
char ck;
system("color 4b");
CreateUDN(NUM,11);
do
{
ck=Menu();
switch(ck)
{
case'1':
introduce();
printf("\n\n\t\t\t%-25s\n\n",G.vex[0].description);
getchar();
getchar();
break;
case '2':
system("cls");
pingmu();
printf("\n\n\t\t\t请选择起点景点(1~10):");
scanf("%d",&v0);
printf("\t\t\t请选择终点景点(1~10):");
scanf("%d",&v1);
ShortestPath(v0); // 计算两个景点之间的最短路径
output(v0,v1); // 输出结果
printf("\n\n\t\t\t\t请按回车键继续...\n");
getchar();
getchar();
break;
case '3':search();
break;
case'5':
PrintMGraph();
printf("\n\n\t\t\t\t请按回车键继续...\n");
getchar();
getchar();
break;
};
}while(ck!='e');
}
char Menu() // 主菜单 //
{
char c;
int flag;
do{
flag=1;
system("cls");
pingmu();
introduce();
printf("\n\t\t┏━━━━━━━━━━━━━━━━━━━┑\n");
printf("\t\t ┃ ┃\n");
printf("\t\t ┃ 1.学校简介 ┃\n");
printf("\t\t ┃ 2.查询景点路径 ┃\n");
printf("\t\t ┃ 3.查询景点信息 ┃\n");
printf("\t\t ┃ 5.查询各景点之间的距离 ┃\n");
printf("\t\t ┃ e.退出 ┃\n");
printf("\t\t ┃ ┃\n");
printf("\t\t ┗━━━━━━━━━━━━━━━━━━━┛\n");
printf("\t\t\t\t请输入您的选择:");
scanf("%c",&c);
if(c=='1'||c=='2'||c=='3'||c=='5'||c=='e')
flag=0;
}while(flag);
return c;
}
char SearchMenu() // 查询子菜单
{
char c;
int flag;
do{
flag=1;
system("cls");
pingmu();
introduce();
printf("\n\t\t ┏━━━━━━━━━━━━━━━━━━┑\n");
printf("\t\t ┃ ┃\n");
printf("\t\t ┃ 1、按照景点编号查询 ┃\n");
printf("\t\t ┃ 2、按照景点名称查询 ┃\n");
printf("\t\t ┃ e、返回 ┃\n");
printf("\t\t ┃ ┃\n");
printf("\t\t ┗━━━━━━━━━━━━━━━━━━┛\n");
printf("\t\t\t请输入您的选择:");
scanf("%c",&c);
if(c=='1'||c=='2'||c=='e')
flag=0;
}while(flag);
return c;
}
void search() // 查询景点信息
{
int num;
int i;
char c;
char name[20];
do
{
system("cls");
c=SearchMenu();
switch (c)
{
case '1':
system("cls");
introduce();
pingmu();
printf("\n\n\t\t请输入您要查找的景点编号:");
scanf("%d",&num);
for(i=0;i<NUM;i++)
{
if(num==G.vex[i].number)
{
printf("\n\n\t\t\t您要查找景点信息如下:");
printf("\n\n\t\t\t%-25s\n\n",G.vex[i].description);
printf("\n\t\t\t按任回车返回...");
getchar();
getchar();
break;
}
}
if(i==NUM)
{
printf("\n\n\t\t\t没有找到!");
printf("\n\n\t\t\t按回车键返回...");
getchar();
getchar();
}
break;
case '2':
system("cls");
pingmu();
introduce();
printf("\n\n\t\t请输入您要查找的景点名称:");
scanf("%s",name);
for(i=1;i<NUM;i++)
{
if(!strcmp(name,
G.vex[i].sight))
{
printf("\n\n\t\t\t您要查找景点信息如下:");
printf("\n\n\t\t\t%-25s\n\n",G.vex[i].description);
printf("\n\t\t\t按回车键返回...");
getchar();
getchar();
break;
}
}
if(i==NUM)
{
printf("\n\n\t\t\t没有找到!");
printf("\n\n\t\t\t按回车键返回...");
getchar();
getchar();
}
break;
}
}while(c!='e');
}
void CreateUDN(int v,int a) // 创建图的函数
{
int i,j;
G.vexnum=v; // 初始化结构中的景点数和边数
G.arcnum=a;
for(i=1;i<G.vexnum;++i) G.vex[i].number=i; // 初始化每一个景点的编号
// 初始化没一个景点名及其景点描述
G.vex[0].sight="学校简介";
G.vex[1].sight="校大门";
G.vex[2].sight="教学楼";
G.vex[3].sight="中心广场";
G.vex[4].sight="山顶操场";
G.vex[5].sight="学生宿舍";
G.vex[6].sight="图书馆";
G.vex[7].sight="体育馆";
G.vex[8].sight="二食堂";
G.vex[9].sight="服务楼";
G.vex[10].sight="北门";
// 这里把所有的边假定为32767,含义是这两个景点之间是不可到达
for(i=1;i<G.vexnum;++i)
{
for(j=1;j<G.vexnum;++j)
{
G.arcs[i][j].adj=Max;
G.arcs[i][j].info=NULL;
}
}
//下边是可直接到达的景点间的距离,由于两个景点间距离是互相的,
// 所以要对图中对称的边同时赋值。
G.arcs[1][4].adj=G.arcs[4][1].adj=200;
G.arcs[1][3].adj=G.arcs[3][1].adj=500;
G.arcs[3][5].adj=G.arcs[5][3].adj=100;
G.arcs[3][10].adj=G.arcs[10][3].adj=400;
G.arcs[4][6].adj=G.arcs[6][4].adj=200;
G.arcs[2][5].adj=G.arcs[5][2].adj=200;
G.arcs[2][4].adj=G.arcs[4][2].adj=300;
G.arcs[5][7].adj=G.arcs[7][5].adj=500;
G.arcs[4][6].adj=G.arcs[6][4].adj=400;
G.arcs[4][7].adj=G.arcs[7][4].adj=600;
G.arcs[6][8].adj=G.arcs[8][6].adj=500;
G.arcs[7][8].adj=G.arcs[8][7].adj=300;
G.arcs[6][9].adj=G.arcs[9][6].adj=500;
}
// 打印出邻接矩阵
void PrintMGraph()
{
int i,j;
cout<<"\n ====================================================================\n\n ";
for(i=1;i<G.vexnum;++i)
{
cout<<G.vex[i].sight<<" ";
}
cout<<endl;
for(i=1;i<G.vexnum;++i)
{
cout<<"\n\n"<<G.vex[i].sight<<" ";
for(j=1;j<G.vexnum;++j)
{
if(G.arcs[i][j].adj==Max)
cout<<" no ";
else
cout<<" "<<G.arcs[i][j].adj;
}
}
cout<<"\n\n\n\n==========================================================================================\n\n\n";
}
void introduce() // 介绍函数
{
int i;
for(i=1;i<=NUM;i++)
{
G.vex[0].description="河南城建学院坐落在国家旅游城市\n\n\t\t国家历史文化名城--平顶山,校园椰风流韵、芳林叠翠、风景秀丽。\n\n\t\t经过二十多年的发展,学校现已形成以城建为主要办学特色\n\n\t\t文、管、理、经等多学科协调发展的格局,是河南省培养城建类\n\n\t\t高级应用型人才的重要基地.目前,学校确立了立足河南\n\n\t\t逐渐面向全国服务面向定位,充分发挥学校特色\n\n\t\t积极扩大对外交流与合作,学术交流日趋\n\n\t\t频繁,国际影响不断增强\n\n\t\t下面几点是河南城建学院的办学特色:\n\n\t\t办学历史较为悠久\n\n\t\t学科专业较为齐全\n\n\t\t师资队伍素质优良\n\n\t\t教学成果较为丰硕\n\n\t\t科研水平不断提高\n\n\t\t校园文化丰富活跃\n\n\t\t人才培养成效显著\n\n\t\t合作交流日趋频繁\n\n\t\t";
G.vex[1].description="学校大门,对面是祥云公园\n\t\t是我们学生休闲娱乐的好地方";
G.vex[2].description="计教系办公大楼,计算机科学技术的科研中心";
G.vex[3].description="这里是学校的主要的风景区,是学校的标志之一";
展开阅读全文