校园导航——数据结构作业(一)
2016-01-11 11:40
537 查看
算法:Dijkstra最短路,DFS
数据结构:邻接矩阵
数据结构:邻接矩阵
// xydy.cpp : 定义控制台应用程序的入口点。 // //#include "stdafx.h" #include "iostream" #include "cstdio" #include "string" #include "cstring" #include "stack" #define N 100 #define INF 200 #define max(a,b) a>b?a:b #define min(a,b) a<b?a:b using namespace std; struct Node { int num; //景点代码 string name;//景点名称 string pro; //简介 }; Node school = { { 1,"行政楼","" },{ 2,"食堂","" }, { 3,"赛博楼","信息分院办公室所在地"},{ 4,"求是楼","实验楼计算机中心"}, { 5,"格致楼","法学管理学院" },{ 6,"工程实习中心","金工实习" }, { 7,"仰仪楼","机电计测分院" },{ 8,"体育馆","旁边有篮球场`足球场`还有网球场" }, { 9,"一号教学楼","主要以阶梯教室为主"},{ 10,"二号教学楼","小教室为多" } }; long long Edge ; //邻接矩阵存路径 int nodenum; //节点总数 void Initial() { nodenum = 10; memset(Edge, -1, sizeof(Edge)); } void Insert_node() { cout << "请输入:编号(0结束添加) 景点名 简介" << endl; int n; while (cin >> n&&n) { bool flag = 0; string name, pro; cin >> name >> pro; for (int i = 0; i < nodenum; i++) { if (school[i].num == n) { cout << "编号重复,请重新输入编号" << endl; flag = 1; break; } } if (flag == 1) continue; nodenum++; school[nodenum - 1].num = n; school[nodenum - 1].name = name; school[nodenum - 1].pro = pro; } } void Insert_edge() { cout << "请输入:起始景点编号 终止景点编号 路径长度(0 0 -1结束)" << endl; int from, to; long long value; while (cin >> from >> to >> value && from && to && (value!=-1)) { bool flag1 = 0, flag2 = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == from) flag1 = 1; if (school[i].num == to) flag2 = 1; } if (flag1 == 1 && flag2 == 1) { Edge[from][to] = value; Edge[to][from] = value; } else cout << "编号错误,重新输入" << endl; } } void Insert() { cout << "添加:1.添加景点 2.添加道路"<<endl; int n; cin >> n; switch (n) { case 1:Insert_node(); break; case 2:Insert_edge(); break; default:cout << "输入错误"; break; } } void Modify() { cout << "修改:修改景点的编号(0结束) 景点修改 简介修改"<<endl; int n; while (cin >> n&&n) { bool flag = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == n) { cin >> school[i].name >> school[i].pro; flag = 1; } } if (flag == 0) cout << "无此编号,重新输入" << endl; } } void Delete_node() { cout << "请输入:景点编号(0结束)" << endl; int n; while (cin >> n&&n) { bool flag = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == n) { for (int k = 0; k < nodenum; k++) //删路径 { Edge [k] = -1; Edge[k] = -1; } for (int j = i; j < nodenum-1; j++) { school[j].num = school[j + 1].num; school[j].name = school[j + 1].name; school[j].pro = school[j + 1].pro; } nodenum--; flag = 1; } } if (flag == 0) cout << "无此编号,重新输入" << endl; } } void Delete_edge() { cout << "请输入:起始景点编号 终止景点编号(0 0结束)" << endl; int from, to; while (cin >> from >> to&&from&&to) { bool flag1 = 0, flag2 = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == from) flag1 = 1; if (school[i].num == to) flag2 = 1; } if (flag1 == 1 && flag2 == 1) { Edge[from][to] = -1; Edge[to][from] = -1; } else cout << "编号错误,重新输入" << endl; } } void Delete() { cout << "删除:1.删除景点 2.删除道路" << endl; int n; cin >> n; switch (n) { case 1:Delete_node(); break; case 2:Delete_edge(); break; default:cout << "输入错误"; break; } } void Display() { for (int i = 0; i < nodenum; i++) { cout << school[i].num <<"\t"<< school[i].name<<"\t" << school[i].pro<<"\n"; } } int maxnum() //最大编号 { int max_num = -INF; for (int i = 0; i < nodenum; i++) max_num = max(max_num, school[i].num); return max_num; } void Showallway() { int max_num = maxnum(); cout << "所有相邻点连通的道路\t长度" << endl; for (int i = 1; i <= max_num; i++) { for (int j = i; j <= max_num; j++) { if (Edge[i][j]>=0) cout << i << "<——>" << j<<"\t\t"<< Edge[i][j] << endl; } } } void Shortway() { cout << "请输入:出发景点编号 终点景点编号(0 0结束)" << endl; int from, to; while (cin >> from >> to && from && to) { long long tempEdge ; memset(tempEdge, 0, sizeof(tempEdge)); int flag1 = 0,flag2 = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == from) flag1 = 1; if (school[i].num == to) flag2 = 1; } ///////////////////////////////////////////////////////// if (flag1 == 1 && flag2 == 1) { bool visit ; memset(visit, 0, sizeof(visit)); long long path_next ; //记录路径,当前结点的后继节点 long long max_num = -INF; //最大编号 max_num = maxnum(); visit[from] = 1; while (true) //最短路Dijstra { if (visit[to]) break; long long min_edge = INF, min_nodej = INF, min_nodei; for (int i = 1; i <= max_num; i++) { if (visit[i] == 1) { for (int j = 1; j <= max_num; j++) { if (Edge[i][j] < min_edge && !visit[j] && Edge[i][j] != -1) { min_edge = Edge[i][j]; min_nodej = j; min_nodei = i; } } } } visit[min_nodej] = 1; tempEdge[min_nodej] = Edge[min_nodei][min_nodej] + tempEdge[min_nodei]; path_next[min_nodei] = min_nodej; } long long cur = from; cout << "最短路长度:" << tempEdge[to] << endl <<"路径:"; while (true) { if (cur == to) { cout << cur << endl; break; } cout << cur << "——>"; cur = path_next[cur]; } } else cout << "编号错误,重新输入" << endl; } /* 1 2 3 1 4 2 2 4 0 2 3 2 3 4 4 0 0 0 */ } void Allway() { cout << "请输入:出发景点编号 终点景点编号" << endl; int from, to; while (cin >> from >> to && from && to) { int flag1 = 0, flag2 = 0; for (int i = 0; i < nodenum; i++) { if (school[i].num == from) flag1 = 1; if (school[i].num == to) flag2 = 1; } //////////////////////////////////////////////////// if (flag1 == 1 && flag2 == 1) { int visit ,vis ; //边,点 访问 memset(visit, 0, sizeof(visit)); memset(vis, 0, sizeof(vis)); int path_len; int path_next ; //记录路径 //memset(path_next, 0, sizeof(path_next)); stack<int>Stack; Stack.push(from); vis[from]++; while (!Stack.empty()) { int cur = Stack.top(); bool flag = 0; for (int i = 1; i <= maxnum(); i++) { p1:; path_len = 0; //路径长度 if (Edge[cur][i] >= 0 && !visit[cur][i]&& !vis[i]) { if (i == to) { path_next[cur] = i; int cur1 = from; while (cur1 != to) { path_len += Edge[cur1][path_next[cur1]]; cout << cur1<<"——>"; cur1 = path_next[cur1]; } cout << to << "\t\t道路长为:" << path_len <<endl; //visit[cur][i]++; i++; goto p1; } visit[cur][i]++; vis[i]++; Stack.push(i); path_next[cur] = i; flag = 1; break; } } if (flag == 0) { Stack.pop(); vis[cur] = 0; //// } } } else cout << "编号错误,重新输入" << endl; } /* 1 2 3 1 5 2 2 5 1 2 3 4 3 5 3 3 4 1 4 5 2 0 0 0 */ } void Query() { cout << "查询:1.显示所有景点信息 2.显示所有路径信息 3.A-B最短路 4.A-B所有路径"<<endl; int n; cin >> n; switch (n) { case 1:Display(); break; case 2:Showallway(); break; case 3:Shortway(); break; case 4:Allway(); break; default:cout << "输入错误"; break; } } int main() { cout << "操作菜单:1.添加 2.修改 3.删除 4.查询 0.结束" << endl; int n; Initial(); while (cin>>n&&n) { switch (n) { case 1:Insert(); break; case 2:Modify(); break; case 3:Delete(); break; case 4:Query(); break; default: break; } cout << "操作菜单:1.添加 2.修改 3.删除 4.查询 0.结束" << endl; } return 0; }