同前几篇博客
算法:组合数学中文第4版 机械工业出版社 P328
////////////////////////////////////////////// // // // Project Name: PrimTree // // // // File Name: P_Tree.h // // // // Author: Victor Zhang // // // // ID: 21*****92 // // // // Create Date: May 20. 2009 // // // ////////////////////////////////////////////// #include <iostream> #include <fstream> using namespace std; struct Edge { int point_a; int point_b; int weigh; Edge* next; }; struct Point { int value; Point* next; }; class P_Tree { private: Edge* EdgeHead; Point* PHead; ofstream outputFile; int TotalWeigh; bool DelEdge(int, int); void DelAll(); bool AddPoint(int); void FindNext(); bool FindPoint(int); public: P_Tree() { EdgeHead = NULL; PHead = NULL; TotalWeigh = 0; outputFile.open("Graph_output.txt", ios::out); }; bool AddEdge(int, int, int); void Prim(); bool ReadFromFile(); ~P_Tree() { if (EdgeHead) DelAll(); TotalWeigh = 0; outputFile.close(); }; };
////////////////////////////////////////////// // // // Project Name: PrimTree // // // // File Name: P_Tree.cpp // // // // Author: Victor Zhang // // // // ID: 21*****92 // // // // Create Date: May 20. 2009 // // // ////////////////////////////////////////////// #include <iostream> #include <fstream> #include <iomanip> #include "P_Tree.h" using namespace std; bool P_Tree::AddEdge(int x, int y, int w) { if (x == y) return false; if (!(this->EdgeHead)) { Edge* pH = new Edge; if (!pH) return false; pH->next = NULL; pH->point_a = (x > y) ? x : y; pH->point_b = (x > y) ? y : x; pH->weigh = w; this->EdgeHead = pH; return true; } else { Edge* p = this->EdgeHead; Edge* pH; while ((p->next) && (p->next->weigh <= w)) { p = p->next; }; if ((p->next) && (p->weigh <= w)) { pH = new Edge; if (!pH) return false; pH->next = p->next; pH->weigh = w; pH->point_a = (x > y) ? x : y; pH->point_b = (x > y) ? y : x; p->next = pH; } else if (p->weigh <= w) { pH = new Edge; if (!pH) return false; pH->next = NULL; pH->weigh = w; pH->point_a = (x > y) ? x : y; pH->point_b = (x > y) ? y : x; p->next = pH; } else { pH = new Edge; if (!pH) return false; pH->next = p; pH->weigh = w; pH->point_a = (x > y) ? x : y; pH->point_b = (x > y) ? y : x; this->EdgeHead = pH; }; return true; }; }; bool P_Tree::DelEdge(int x, int y) { if (x == y) return false; Edge* p; Edge* pp; Edge* pc; p = this->EdgeHead; if (!p) return false; pp = p->next; if (x < y) { int t = x; x = y; y = t; }; while (p && (p->point_a == x) && (p->point_b == y)) { pp = p->next; delete p; p = pp; this->EdgeHead = pp; }; if (!p) return true; pp = p->next; while (pp) { while (pp && (pp->point_a == x) && (pp->point_b == y)) { pc = pp; pp = pp->next; delete pc; p->next = pp; }; if (!pp) return true; p = pp; pp = p->next; }; return true; }; void P_Tree::DelAll() { Edge* p; Point* pP; while (this->EdgeHead) { p = this->EdgeHead->next; delete this->EdgeHead; this->EdgeHead = p; }; while (this->PHead) { pP = this->PHead->next; delete this->PHead; this->PHead = pP; }; }; bool P_Tree::AddPoint(int v) { Point* p = new Point; p->value = v; p->next = this->PHead; this->PHead = p; return true; }; bool P_Tree::FindPoint(int v) { Point* p; p = this->PHead; while (p && (p->value != v)) p = p->next; if (p) return true; return false; }; void P_Tree::FindNext() { if (!(this->EdgeHead)) return; if (!(this->PHead)) { this->outputFile<<"("<<this->EdgeHead->point_a<<","<<this->EdgeHead->point_b<<")\n"; cout<<"("<<this->EdgeHead->point_a<<","<<this->EdgeHead->point_b<<")\n"; this->AddPoint(this->EdgeHead->point_a); this->AddPoint(this->EdgeHead->point_b); this->TotalWeigh += this->EdgeHead->weigh; this->DelEdge(this->EdgeHead->point_a, this->EdgeHead->point_b); return; } else { int NewP; Edge* p; Point* pP; p = this->EdgeHead; while(p) { if (this->FindPoint(p->point_a)) { this->outputFile<<"("<<p->point_a<<","<<p->point_b<<")\n"; cout<<"("<<p->point_a<<","<<p->point_b<<")\n"; NewP = p->point_b; this->TotalWeigh += p->weigh; this->AddPoint(NewP); pP = this->PHead; while (pP) { this->DelEdge(NewP, pP->value); pP = pP->next; }; return; }; if (this->FindPoint(p->point_b)) { this->outputFile<<"("<<p->point_a<<","<<p->point_b<<")\n"; cout<<"("<<p->point_a<<","<<p->point_b<<")\n"; NewP = p->point_a; this->TotalWeigh += p->weigh; this->AddPoint(NewP); pP = this->PHead; while (pP) { this->DelEdge(NewP, pP->value); pP = pP->next; }; return; }; p = p->next; }; return; }; }; void P_Tree::Prim() { while (this->EdgeHead) this->FindNext(); cout<<this->TotalWeigh<<endl; this->outputFile<<this->TotalWeigh<<endl; }; bool P_Tree::ReadFromFile() { ifstream inputFile ("Graph_data.txt", ios::in); if (!inputFile) { cout<<"Error in reading file :\"Graph_data.txt\"."<<endl; system("pause"); return false; }; try { int i; int j; int r; i = j = r = 0; inputFile>>i>>j>>r; if (!(this->AddEdge(i, j, r))) return false; while(inputFile>>i>>j>>r) if (!(this->AddEdge(i, j, r))) return false; } catch(...) { cout<<"Error in reading file :\"Graph_data.txt\"."<<endl; system("pause"); inputFile.close(); return false; }; inputFile.close(); return true; };
////////////////////////////////////////////// // // // Project Name: PrimTree // // // // File Name: main.cpp // // // // Author: Victor Zhang // // // // ID: 21*****92 // // // // Create Date: May 20. 2009 // // // ////////////////////////////////////////////// #include <iostream> using namespace std; #include "P_Tree.h" void main() { P_Tree a; a.ReadFromFile(); a.Prim(); system("pause"); };样例输入文件:
1 6 10
1 2 28
2 7 14
2 3 16
6 5 25
7 5 24
7 4 18
5 4 22
3 4 12