您的位置:首页 > 其它

最大团问题

2015-10-20 10:19 211 查看
#include "cstdio"
#include "queue"
#include "cstring"
#define MAX 20
using namespace std;

int n;  //城市数量
int x[MAX];  //解向量

struct Node
{
int cn;   //当前团中的顶点数
int un;   //当前团最大顶点的上界,优先级
int level;  //结点在子集空间树中所处的层次

//最大顶点上界最大的结点先出队列
bool operator < (const Node &node) const
{
return un < node.un;
}
};

priority_queue<Node> pq;

void EnQueue(int cn, int un, int level)
{
Node node;
node.cn = cn;
node.un = un;
node.level = level;
pq.push(node);
}

int maxClique(int a[6][6])
{
memset(x, 0, sizeof(x));
int bestn = 0;  //最大团中顶点数最优值
int i = 1;  //结点所在层次
int cn = 0;  //当前最大团中顶点数
int j;
int ok;
Node node;  //当前扩展结点
while(i!=n+1)  //如果还没有到叶结点
{
ok = 1;
//检查当前顶点是否与团中其它顶点相连,如果相连,可以加入团
for(j=1; j<i; j++)
if(x[j] && !a[i][j])
{
ok = 0;
break;
}
if(ok)  //搜索左子树
{
if(cn+1>bestn)  //如果加入顶点后的顶点数比当前最优值更优
bestn = cn+1;    //更新最优值
x[i] = 1;   //顶点加入团
EnQueue(cn+1, cn+n-i+1, i+1);
}
if(cn+n-i>=bestn)   //如果可能产生最优值,搜索右子树
{
//x[i] = 0;  //不加入
EnQueue(cn, cn+n-i, i+1);
}

//取下一层扩展结点
node = pq.top();
pq.pop();
cn = node.cn;
i = node.level;
}
return bestn;
}

int main()
{
n = 5;
int a[6][6] = {
{0, 0, 0, 0, 0, 0},
{0, 0, 1, 0, 1, 1},
{0, 1, 0, 1, 0, 1},
{0, 0, 1, 0, 0, 1},
{0, 1, 0, 0, 0, 1},
{0, 1, 1, 1, 1, 0}
};
printf("邻接矩阵为:\n");
int i, j;
for(i=1; i<=n; i++)
{
for(j=1; j<=n; j++)
printf("%d ", a[i][j]);
printf("\n");
}
int bestn = maxClique(a);
printf("最大团顶点数:%d\n", bestn);
printf("解向量之一为:\n");
for(i=1; i<=n; i++)
printf("%d ", x[i]);
printf("\n");
return 0;
}


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: