小根堆头文件:
#include "stdafx.h"
#include <vector>
#include <iostream>
#include <iomanip>
using namespace std;
template<typename DataType>
class MinHeap
{
public:
MinHeap();
MinHeap(int);
MinHeap( DataType[], int);
MinHeap( vector<DataType> );
bool removeTop();
DataType getTop();
bool insert( DataType );
bool empty() const;
void display() const;
private:
int capacity;
int size;
DataType * topPointer;
void displayAux( int, int ) const;
};
template<typename DataType>
MinHeap<DataType>::MinHeap()
{
size = 0;
capacity = 10;
topPointer = new DataType[capacity + 1];
}
template<typename DataType>
MinHeap<DataType>::MinHeap(int capacity)
{
size = 0;
this.capacity = capacity;
topPointer = new DataType[capacity + 1];
}
template<typename DataType>
MinHeap<DataType>::MinHeap(DataType arr[], int num)
{
size = 0;
capacity = num;
topPointer = new DataType[capacity + 1];
for(int i = 0; i < num; i++)
insert( arr[i] );
}
template<typename DataType>
MinHeap<DataType>::MinHeap( vector<DataType> vec )
{
size = 0;
capacity = vec.size();
topPointer = new DataType[capacity + 1];
for(int i = 0; i < capacity; i++)
insert( vec.at(i) );
}
template<typename DataType>
DataType MinHeap<DataType>::getTop()
{
return *(topPointer + 1);
}
template<typename DataType>
bool MinHeap<DataType>::removeTop()
{
*(topPointer + 1) = *(topPointer + size);
int start = 1;
int end = size;
int next = 2*start;
while( next <= end )
{
if( next < end )
{
if( *(topPointer + next) > *(topPointer + next + 1) )
next = next + 1;
}
if( *(topPointer + start) > *(topPointer + next ) )
{
DataType tmp = *(topPointer + start);
*(topPointer + start) = *(topPointer + next);
*(topPointer + next) = tmp;
}
start = next;
next = 2*start;
}
size--;
return true;
}
template<typename DataType>
bool MinHeap<DataType>::insert(DataType item)
{
if( ++size <= capacity )
*(topPointer + size) = item;
else
return false;
int start = size;
int next = size/2;
while( next > 0 && *(topPointer + start) < *(topPointer + next) )
{
DataType tmp = *(topPointer + next);
*(topPointer + next) = *(topPointer + start);
*(topPointer + start) = tmp;
start = next;
next = start/2;
}
return true;
}
template<typename DataType>
bool MinHeap<DataType>::empty() const
{
return(0 == size);
}
template<typename DataType>
void MinHeap<DataType>::display() const
{
displayAux(1,0);
}
template<typename DataType>
void MinHeap<DataType>::displayAux(int index, int indent) const
{
if( index <= size )
{
displayAux( index * 2 , indent + 20 );
cout << setw(indent) << *( topPointer + index) << endl;
displayAux( index * 2 + 1, indent + 20 );
}
else
return;
}
Kruskal头文件:
#include <iostream>
using namespace std;
class NodeEdge
{
public:
NodeEdge():startNode(0),endNode(0),distance(0){}
NodeEdge(int start, int end):startNode(start),endNode(end){}
NodeEdge(int start, int end, int dis):startNode(start),endNode(end),distance(dis){}
const NodeEdge & operator = ( const NodeEdge & );
void display( ostream & out ) const;
public:
int startNode;
int endNode;
int distance;
};
bool operator < ( const NodeEdge & left, const NodeEdge & right )
{
if( left.distance < right.distance )
return true;
else
return false;
}
bool operator > ( const NodeEdge & left, const NodeEdge & right )
{
if( left.distance > right.distance )
return true;
else
return false;
}
const NodeEdge & NodeEdge::operator = ( const NodeEdge & rightSide )
{
if( this != & rightSide )
{
this->startNode = rightSide.startNode;
this->endNode = rightSide.endNode;
this->distance = rightSide.distance;
}
return *this;
}
void NodeEdge::display( ostream & out ) const
{
out << startNode <<"<---> " << endNode <<"(" << distance <<")";
}
ostream & operator << ( ostream & out, const NodeEdge & nodeEdge )
{
nodeEdge.display( out );
return out;
}
Kruskal源文件:
// Kruskal.cpp : 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include "MinHeap.h"
#include "Kruskal.h"
#include <vector>
const int NUM = 7;
int getNodeRoot(int index);
int map[NUM][NUM] = { {0, 28, INT_MAX, INT_MAX, INT_MAX, 10, INT_MAX},
{28, 0, 16, INT_MAX, INT_MAX, INT_MAX, 14},
{0, 16, 0, 12, INT_MAX, INT_MAX, INT_MAX},
{INT_MAX, INT_MAX, 12, 0, 22, INT_MAX, 18},
{INT_MAX, INT_MAX, INT_MAX, 22, 0, 25, 24},
{10, INT_MAX, INT_MAX, INT_MAX, 25, 0, INT_MAX},
{INT_MAX, 14, INT_MAX, 18, 24, INT_MAX, 0} };
bool nodeVisited[NUM + 1] = {false};
int nodeRank[NUM + 1] = {0};
int nodeRoot[NUM + 1];
int _tmain(int argc, _TCHAR* argv[])
{
//int a[10] = {4,2,6,9.1,23,54,32,95,23.3};
//MinHeap<int> MinHeap(a,10);
//MinHeap.display();
vector<NodeEdge> nodeVec;
for(int i = 0; i < NUM + 1; i++)
nodeRoot[i] = i;
for(int i = 0; i < NUM; i++)
{
for(int j = i + 1; j < NUM; j++)
{
if(map[i][j] != INT_MAX)
nodeVec.push_back( NodeEdge(i+1,j+1,map[i][j]) );
}
}
MinHeap<NodeEdge> nodeMinHeap( nodeVec );
nodeVec.clear();
nodeMinHeap.display();
while( !nodeMinHeap.empty() )
{
NodeEdge tmp = nodeMinHeap.getTop();
int root1 = getNodeRoot( tmp.startNode );
int root2 = getNodeRoot( tmp.endNode );
if( root1 != root2 )
{
nodeVec.push_back( tmp );
if( nodeRank[root1] > nodeRank[root2] )
{
if( nodeRoot[tmp.startNode] != root1 && nodeRoot[ nodeRoot[tmp.startNode] ] == nodeRoot[tmp.startNode] )
nodeRoot[ nodeRoot[tmp.startNode] ] = root1;
if( nodeRoot[tmp.endNode] != root1 && nodeRoot[ nodeRoot[tmp.endNode] ] == nodeRoot[tmp.endNode] )
nodeRoot[ nodeRoot[tmp.startNode] ] = root1;
nodeRoot[ tmp.startNode ] = root1;
nodeRoot[ tmp.endNode ] = root1;
}
else
{
if( nodeRoot[tmp.startNode] != root2 && nodeRoot[ nodeRoot[tmp.startNode] ] == nodeRoot[tmp.startNode] )
nodeRoot[ nodeRoot[tmp.startNode] ] = root2;
if( nodeRoot[tmp.endNode] != root1 && nodeRoot[ nodeRoot[tmp.endNode] ] == nodeRoot[tmp.endNode] )
nodeRoot[ nodeRoot[tmp.startNode] ] = root2;
nodeRoot[ tmp.startNode ] = root2;
nodeRoot[ tmp.endNode ] = root2;
if( nodeRank[root1] == nodeRank[root2] )
nodeRank[root2]++;
}
}
nodeMinHeap.removeTop();
}
for( vector<NodeEdge>::iterator it = nodeVec.begin(); it != nodeVec.end(); it++ )
cout << *it << endl;
return 0;
}
int getNodeRoot( int index )
{
if( nodeRoot[index] != index )
return getNodeRoot( nodeRoot[index] );
else
return index;
}
参考程序:
http://www.codeproject.com/Articles/163618/Kruskal-Algorithm