数据结构图--Prim算法

// Graph_Pra.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include <iostream>
#include <string>
#include <vector>
#include <queue>
using namespace std;

struct GraphNode {
    string vertexName;
    bool visited;
    float weight;
    int index;
    friend bool operator < (GraphNode a, GraphNode b) {
        return a.weight > b.weight;
    }
};

template <class T>
class Graph {
public:
    Graph(int *vertexArray, T * nameOfVertex, int numberOfVertex);
    void Prim(int source); //Prim算法
    void GetVexInfo(); //取顶点信息
    void GerArcInfo(); //输出边信息
    void SetArc(int vertextFrom, int vertextTo, int arcLength); //修改边
    void DeleteVex(int vertex); 
    void InsertVex(int position, T name);
    void DeleteArc(int vertexFrom, int vertexTo);
    void InsetArc(int vertextFrom, int vertextTo, int value);
    void PrintAdjacencyMatrix();
private:
    int vertexNum, arcNum;
    vector< vector<int> > adjacencyMatrix;
    vector<GraphNode> graphNodeArray;
};
struct Arc {
    int From, To;
    int weight;
};
bool Rule(const Arc & p1, const Arc & p2) {
    if (p1.To < p2.To)
        return true;
    else return false;
}

template<class T>
void Graph<T>::Prim(int source) {
    int  pos = 0 ;

    vector<Arc> CostArc(vertexNum);
    for (int i = 0; i < vertexNum; ++i) {
        CostArc[i].From = source;
        CostArc[i].To = i;
        CostArc[i].weight = adjacencyMatrix[source][i];
    }
    CostArc[source].weight = 0;
    vector<Arc> PrimTree;
    while (PrimTree.size() != vertexNum - 1) {
        pos = 0;
    //    for (int i = 0; i < vertexNum; ++i)    cout << CostArc[i].weight << endl;
        for (int i = 0; i < vertexNum; ++i) {
            if ( (CostArc[pos].weight==0) ||( (CostArc[pos].weight > CostArc[i].weight)&&CostArc[i].weight!=0))
                pos = i;
        }
        PrimTree.push_back(CostArc[pos]);
        CostArc[pos].weight = 0;
        for (int i = 0; i < vertexNum; ++i) {
            if (adjacencyMatrix[pos][i] < CostArc[i].weight) {
                CostArc[i].From = pos;
                CostArc[i].weight = adjacencyMatrix[pos][i];
            }
        }
    }
    sort(PrimTree.begin(), PrimTree.end(), Rule);
    for (int i = 0; i < PrimTree.size(); ++i)
        cout << graphNodeArray[PrimTree[i].From].vertexName << " ---> " << graphNodeArray[PrimTree[i].To].vertexName << "  ";
    return;
}

template <class T>
Graph<T>::Graph(int *vertexArray, T *nameOfVertex, int numberOfVertex) {
    vertexNum = numberOfVertex;
    arcNum = 0;
    GraphNode tempGraphNode;
    for (int i = 0; i < vertexNum; i++) {
        tempGraphNode.vertexName = nameOfVertex[i];
        tempGraphNode.index = i;
        graphNodeArray.push_back(tempGraphNode);
    }
    adjacencyMatrix.resize(vertexNum, vector<int>(vertexNum));
    for(int i = 0 ;  i < vertexNum ; i++)
        for (int j = 0; j < vertexNum; j++) {
            adjacencyMatrix[i][j] = *(vertexArray + i*vertexNum + j);
            if (adjacencyMatrix[i][j] < INT_MAX)
                arcNum++;
        }
    this->arcNum = arcNum / 2;
}

template<class T>
void Graph<T>::PrintAdjacencyMatrix() {
    cout << "图G的顶点数是:" << vertexNum << endl;
    cout << "顶点向量的值是:" << endl;
    for (int i = 0; i < graphNodeArray.size(); i++) {
        cout << graphNodeArray[i].vertexName << endl;
        cout << "图G的边数是" << arcNUm << endl;
        for(int i = 0 ; i <adjacencyMatrix.size() ; i++)
            for (int j = i + 1; j < adjacencyMatrix.size(); j++) {
                for (int j = i + 1; j < adjacencyMatrix.size(); j++)
                    if (adjacencyMatrix[i][j] < INT_MAX)
                        cout << "(" << i << "," << j << adjacencyMatrixp[i][j] << ")" << endl;
            }
    }
}

template<class T>
void Graph<T>::GetVexInfo() {
    for (int i = 0; i < graphNodeArray.size(); i++) {
        cout << graphNodeArray[i].vertexName << "\n";
    }
}

template <class T>
void Graph<T>::SetArc(int vertexFrom, int vertextTo, int arclength) {
    if (vertexFrom > vertexNum || vertextTo > vertexNum)    throw"位置";
    else {
        adjacencyMatrix[vertextFrom][vertextTo] = arclength;
        adjacencyMatrix[vertexTo][vertextFrom] = arclength;
    }
}

template<class T>
void Graph<T>::GerArcInfo() {
    for (int i = 0; i < graphNodeArray.size(); i++) {
        for (int j = 0; j < i; j++) {
            if (adjacencyMatrix[i][j] < INT_MAX)
                cout << "从" << graphNodeArray[i].vertexName << "到" << graphNodeArray[i].vertexName
                << "的路径长度为:" << adjacencyMatrix[i][j] << "\n";
        }
    }
}

template<class T>
void Graph<T>::InsertVex(int position, T name) {
    if (position < 0 || position>graphNodeArray.size())
        throw"位置不正确";
    vector<int> tempRow(graphNodeArray.size(), INT_MAX);
    GraphNode tempGraphNode;
    tempGraphNode.vertexName = name;
    graphNodeArray.insert(graphNodeArray.begin() + position, tempGraphNode);
    adjacencyMatrix.insert(adjacencyMatrix.begin() + position, tempRow);
    for (unsigned i = 0; i < graphNodeArray.size(); ++i) {
        adjacencyMatrix[i].insert(adjacencyMatrix[i].begin() + position, INT_MAX);
    }
    this->vertexNum = this->vertexNum + 1;
}

template <class T>
void Graph<T>::DeleteVex(int position) {
    if (position<0 || position>adjacencyMatrix.size())    throw"位置";
    int vertexNum = adjacencyMatrix.size();
    if (position > -1) {
        graphNodeArray.erase(graphNodeArray.begin() + position);
        if (adjacencyMatrix.size() > position) {
            adjacencyMatrix.erase(adjacencyMatrix.begin() + position);
        }
        for (unsigned i = 0; i < adjacencyMatrix.size(); ++i) {
            if (adjacencyMatrix[i].size() > position) {
                if (adjacencyMatrix[i][position] != INT_MAX) {
                    this->arcNum = this->arcNum - 1;
                }
                adjacencyMatrix[i].erase(adjacencyMatrix[i].begin() + position);
            }
        }
        this->vertexNum = this->vertexNum - 1;
    }
}

template<class T>
void Graph<T>::DeleteArc(int vertextForm, int vertextTo) {
    if (vertextForm > vertexNum || vertextTo > vertexNum)    throw"位置";
    adjacencyMatrix[vertextForm][vertextTo] =
        adjacencyMatrix[vertexTo][vertextForm] = INT_MAX;
    this->arcNum = this->arcNum - 1;
}

template <class T>
void Graph<T>::InsetArc(int vertextFrom, int vertextTo, int value) {
    if (vertextFrom > vertexNum || vertextTo > vertexNum) throw"位置";
    if (adjacencyMatrix[vertextFrom][vertextTo] == INT_MAX) {
            adjacencyMatrix[vertextFrom][vertextTo] = value;
            adjacencyMatrix[vertextTo][vertextFrom] = value;
            cout << "从" << graphNodeArray[vertextFrom].vertexName << "到" << graphNodeArray[vertextTo].vertexName
                << "的路径长度为:" << adjacencyMatrix[vertextFrom][vertextTo] << "\n";
            this->arcNum = this->arcNum + 1;
    }
    else {
        cout << "边已经存在!" << endl;
    }
}


int main()
{
    const int numofVertex = 7;
    int cost[numofVertex][numofVertex] = {
        {INT_MAX,12,5,11,INT_MAX,INT_MAX,INT_MAX},
        {12,INT_MAX,INT_MAX,INT_MAX,33,INT_MAX,INT_MAX},
        {5,INT_MAX,INT_MAX,21,INT_MAX,19,INT_MAX},
        {11,INT_MAX,21,INT_MAX,28,8,INT_MAX},
        {INT_MAX,33,INT_MAX,28,INT_MAX,INT_MAX,6},
        {INT_MAX,INT_MAX,19,8,INT_MAX,INT_MAX,16},
        {INT_MAX,INT_MAX,INT_MAX,INT_MAX,6,16,INT_MAX}
    };
    string verName[numofVertex] = { "A","B","C","D","E","F","G" };
    Graph<string> g(*cost, verName, numofVertex);
    int source;
    cout << "请输入Prim算法初始顶点:" << "\n";
    cin >> source;
    try {
        g.Prim(source);
    }
    catch (char *) {
        cout << "Prim 算法计算失败" << endl;
    }
    system("pause");
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值