數據結構課程設計——校園導游系統(圖)


數據結構課程設計——校園導游系統

主要的任務為兩個:

  1. 求兩點間最短路徑。(迪傑斯特拉算法)
  2. 求兩點間簡單路徑。(dfs)

難度不大。部分有注釋。

//先是MGraph中的主要算法實現
#ifndef MGRAPH_H_INCLUDED
#define MGRAPH_H_INCLUDED

#include <iostream>
#include <algorithm>
#include <string>

using namespace std;

#define MAX_VEX 20
#define MAX_NUM 32767

typedef struct vex
{
    string name;
    string info;
} vex, *vexptr;


//圖的鄰接矩陣存儲表示
typedef struct
{
    vex vexs[MAX_VEX];                    //頂點表
    int arcs[MAX_VEX][MAX_VEX];        //鄰接矩陣
    int vexnum, arcnum;                 //圖的當前點數和邊數
} MGraph;


//獲取頂點位置:若G中存在頂點u,則返回該頂點在圖中的位置;否則返回其他信息
int LocateVex(MGraph &G, string u)
{
    int index = -1;                         //原始下標,沒找到元素返回-1
    for(int i = 0; i < G.vexnum; i++)      //遍歷頂點數組
    {
        if(u == G.vexs[i].name)
        {
            index = i;                      //記錄元素下標
        }
    }
    return index;                           //返回下標
}

void MapOfHdu()
{
    cout<<"==============簡略地圖(地點括號內為在頂點表中的下標)============="<<endl;
    cout<<"八號樓(8)"<<endl;
    cout<<"                                                      學生活動中心(10) "<<endl;
    cout<<"                                 圖書館(9)"<<endl;
    cout<<""<<endl;
    cout<<"       體育館(5)"<<endl;
    cout<<""<<endl;
    cout<<"                    六號樓(6)             七號樓(7)              "<<endl;
    cout<<""<<endl;
    cout<<"                    四號樓(4)"<<endl;
    cout<<"                                          三號樓(3)"<<endl;
    cout<<"                    二號樓(2)"<<endl;
    cout<<"                                          一號樓(1)"<<endl;
    cout<<"============================南大門(0)============================"<<endl;
}


int CreateMap(MGraph &G)
{
    G.vexnum = 11;//頂點數
    G.arcnum = 17;//邊數

    //初始化鄰接矩陣,所有邊的權值置INF(MAX_NUM)
    for(int i = 0; i < G.vexnum; ++i)
    {
        for(int j = 0; j < G.vexnum; ++j)
        {
            G.arcs[i][j] = MAX_NUM;
        }
    }

    G.vexs[0].name = "南大門";
    G.vexs[0].info = "南大門為學校正大門";
    G.vexs[1].name = "一號樓";
    G.vexs[1].info = "信仁樓";
    G.vexs[2].name = "二號樓";
    G.vexs[2].info = "信義樓";
    G.vexs[3].name = "三號樓";
    G.vexs[3].info = "信禮樓";
    G.vexs[4].name = "四號樓";
    G.vexs[4].info = "在建";
    G.vexs[5].name = "體育館";
    G.vexs[5].info = "體育館簡介";
    G.vexs[6].name = "六號樓";
    G.vexs[6].info = "信誠樓";
    G.vexs[7].name = "七號樓";
    G.vexs[7].info = "信博樓";
    G.vexs[8].name = "八號樓";
    G.vexs[8].info = "信遠樓";
    G.vexs[9].name = "圖書館";
    G.vexs[9].info = "圖書館簡介";
    G.vexs[10].name = "學生活動中心";
    G.vexs[10].info = "學生活動中心簡介";


    //初始化各邊權值
    G.arcs[0][1] = 100;
    G.arcs[0][2] = 100;
    G.arcs[0][3] = 300;
    G.arcs[1][2] = 250;
    G.arcs[1][3] = 100;
    G.arcs[2][3] = 250;
    G.arcs[3][4] = 350;
    G.arcs[3][8] = 1000;
    G.arcs[4][5] = 500;
    G.arcs[4][6] = 300;
    G.arcs[4][8] = 800;
    G.arcs[5][6] = 200;
    G.arcs[5][10] = 900;
    G.arcs[7][8] = 850;
    G.arcs[7][9] = 150;
    G.arcs[7][10] = 250;
    G.arcs[9][10] = 150;

    G.arcs[1][0] = 100;
    G.arcs[2][0] = 100;
    G.arcs[3][0] = 300;
    G.arcs[2][1] = 250;
    G.arcs[3][1] = 100;
    G.arcs[3][2] = 250;
    G.arcs[4][3] = 350;
    G.arcs[8][3] = 1000;
    G.arcs[5][4] = 500;
    G.arcs[6][4] = 300;
    G.arcs[8][4] = 800;
    G.arcs[6][5] = 200;
    G.arcs[10][5] = 900;
    G.arcs[8][7] = 850;
    G.arcs[9][7] = 150;
    G.arcs[10][7] = 250;
    G.arcs[10][9] = 150;

    return 1;
}

//景點介紹
int GetInfo(MGraph &G, string u)
{
    for(int i = 0; i < G.vexnum; i++)
    {
        if(G.vexs[i].name == u)
        {
            cout<<"有關該景點的信息是:";
            cout<< G.vexs[i].info << endl;
            return 1;
        }
    }
    cout << "未查詢到此景點!" << endl;
    return 0;
}

int GetDistance(MGraph &G, string u1,string u2)
{
    int id1,id2;
    id1=LocateVex(G,u1);
    id2=LocateVex(G,u2);
    return G.arcs[id1][id2]<MAX_NUM?G.arcs[id1][id2]:-1;
}

void Dijkstra(MGraph G,int v,int dist[],int path[])
{
    int Set[MAX_VEX];
    int Min,u;
    //對數組進行初始化//
    for(int i=0; i<G.vexnum; i++)
    {
        dist[i]=G.arcs[v][i];
        Set[i]=0;
        if(G.arcs[v][i]<MAX_NUM)
        {
            path[i]=v;
        }
        else
        {
            path[i]=-1;
        }
        Set[v]=1;
        path[v]=-1;
    }
    //關鍵操作//
    for(int i=0; i<G.arcnum-1; i++)
    {
        Min=MAX_NUM;
        //循環每次從剩余頂點中挑出一個頂點,它是S集通往所有頂點的路徑長度最小的那個//
        for(int j=0; j<G.arcnum; j++)
        {
            if(Set[j]==0&&dist[j]<Min)
            {
                u=j;
                Min=dist[j];
            }
        }
        Set[u]=1;//將選出的頂點並入最短路徑中
        //循環以剛並入的頂點對通往剩余頂點的所有路徑進行檢測//
        for(int j=0; j<G.arcnum; j++)
        {
            //if判斷頂點U的加入是否會出現通往頂點j的更短的路徑,如果出現,則改變原來路徑及其長度,否則不變//
            if(Set[j]==0&&dist[u]+G.arcs[u][j]<dist[j])
            {
                dist[j]=dist[u]+G.arcs[u][j];
                path[j]=u;
            }
        }
    }
    //算法結束后,dist[]中存放初始頂點v到其余頂點的最短路徑長度,path[]中存放v到其余頂點的最短路徑//

}


void printPath(int path[],int a)
{
    //path實際上是一顆雙親存儲結構的樹,故需要棧來將其逆序輸出//
    int Stack[MAX_VEX];
    int top=-1;

    while(path[a]!=-1)
    {
        Stack[++top]=a;
        a=path[a];
    }
    Stack[++top]=a;
    while(top!=-1)
    {
        cout<<Stack[top--]<<" ";
    }
    cout<<endl;
}

int visited[MAX_VEX]= {0};
int DFSpath[MAX_VEX]= {0};
int DFStop=-1;

void DFS(MGraph & G,int v,int e)
{
    visited[v]=1;
    DFSpath[++DFStop]=v;

    for(int i=0; i<G.vexnum; i++)
    {
        if(v==e)
        {
            for(int j=0; j<=DFStop; j++)
            {
                cout<<DFSpath[j]<<" ";
            }
            cout<<endl;
            visited[v]=0;
            DFStop--;
            break;
        }

        if((G.arcs[v][i]<MAX_NUM)&&(!visited[i]))
        {
            DFS(G,i,e);
        }

        if(i==G.vexnum-1)//准備回溯前先處理棧和當前節點狀態
        {
            DFStop--;
            visited[v]=0;
        }

    }
}
#endif // MGRAPH_H_INCLUDED

之后是主程序實現。

#include <iostream>
#include "MGraph.h"

using namespace std;

void menu()
{
        cout << "----------------------歡迎咨詢校園導游系統---------------------- "<< endl;
        cout << "--------------------請在屏幕上輸入相應的數字--------------------- "<< endl;
        cout << "                  【1】.  查看地圖                               " << endl;
        cout << "                  【2】.  信息查詢                               " << endl;
        cout << "                  【3】.  最短路徑查詢                           " << endl;
        cout << "                  【4】.  簡單路徑查詢                           " << endl;
        cout << "                  【5】.  退出程序                               " << endl;
        cout<< "-------------------------------------------------------------------" << endl;
}

int main(){
    MGraph G;
    int m;
    string b;
    CreateMap(G);

    while(1){
        menu();
        cin>> m;
        switch(m){
            case 1:
            {
                MapOfHdu();
                system("pause");
                system("cls");
                break;
            }
            case 2:
            {
                MapOfHdu();
                cout << "請輸入要查詢的位置名稱:";
                cin>> b;
                GetInfo(G, b);
                system("pause");
                system("cls");
                break;
            }
            case 3:
            {
                MapOfHdu();
                string v1, v2;
                int v1i,v2i;
                int dist[MAX_VEX],path[MAX_VEX];
                cout << "請輸入起點和終點:(輸入名稱並以空格間隔)";
                cin>> v1 >> v2;
                cout << v1 << "到" << v2 << "的最短路徑長為:";
                v1i=LocateVex(G,v1);
                v2i=LocateVex(G,v2);
                Dijkstra(G,v1i,dist,path);
                cout<<dist[v2i]<<endl;
                cout << v1 << "到" << v2 << "的最短路徑為:";
                printPath(path,v2i);
                cout<< endl;

                system("pause");
                system("cls");
                break;
            }
            case 4:
            {
                MapOfHdu();
                string v1, v2;
                int v1i,v2i;
                cout << "請輸入起點和終點:(輸入名稱並以空格間隔)";
                cin>> v1 >> v2;
                cout << v1 << "到" << v2 << "的所有簡單路徑為:"<<endl;
                v1i=LocateVex(G,v1);
                v2i=LocateVex(G,v2);
                DFS(G,v1i,v2i);
                system("pause");
                system("cls");
                break;
            }

            case 5:
                return 0;
        }
    }
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM