None / maximum independent set to the largest group of FIG.

definition:

Group: identify a set of points from a non-directed graph, edges such that any two points in this set has a directly connected.

Great mission: not to any other sub-group of group of map

The largest group: the largest group in the great group of points

theorem:

A maximum independent set equal to its complement graph of FIG maximum clique


Born_Kerbosch algorithm

Previous enumerated from each point of a first point, where the other point is greater than the selected point. VEC with [] the currently selected record set point, determining whether a point can be selected, if only the need to enumerate the selected point is directly connected.

Optimization: NUM with [] in each case the optimum recording subsequent point (maximum group size), plus the number of the current situation if the optimal point can not be better than the existing answer ans, direct return.

#include<bits/stdc++.h>
using namespace std;
const int maxn=53;
int mp[maxn][maxn];
int ans_vec[maxn],vec[maxn],num[maxn];//num最后是递减的
    //答案团,当前团,每个位置开始遍历得到的最大团
int n,ans;
int dfs(int p,int siz){
    for(int i=p+1;i<=n;i++){//从前往后遍历每个点
        if(num[i]+siz<=ans)return 0;//最优性剪枝
        if(mp[p][i]){
            int can=1;
            for(int j=1;j<=siz;j++){
                if(!mp[vec[j]][i]){
                    can=0;break;
                }
            }
            if(can){//如果和已有集合均有边,则加入集合
                vec[siz+1]=i;
                if(dfs(i,siz+1))return 1;//更优的答案已经记录,无需更新
            }
        }
    }
    if(siz>ans){
        ans=siz;
        for(int i=1;i<=ans;i++)ans_vec[i]=vec[i];
        return 1;
    }
    return 0;
}
int deal(){
    ans=-1;
    for(int i=n;i>=1;i--){
        vec[1]=i;//开始只有i
        dfs(i,1);
        num[i]=ans;
    }
    return ans;
}
int main(){
    cin>>n;
    for(int i=1;i<=n;i++){
        for(int j=1;j<=n;j++){
            scanf("%d",&mp[i][j]);
        }
    }
    int res=deal();
    printf("%d\n",res);
}

Faster and shorter wording:

#include <bits/stdc++.h>
using namespace std;
const int N = 45;
int n, k, g[N][N], ans[N], answer;
void dfs(int sum, int v[], int len) {
    answer = max(answer, sum);
    int v1[N], len1;
    for(int i = 1; i <= len; ++i) {
        if(sum + len - i + 1 <= answer) break;
        if(sum + ans[v[i]] <= answer) break;//最优性剪枝
        len1 = 0;
        for(int j = i + 1; j <= len; ++j) if(g[v[i]][v[j]]) v1[++len1] = v[j];
        dfs(sum + 1, v1, len1);
    }
} 
inline void MaxClique() {
    int valid[N], len;
    answer = ans[n] = 1;
    for(int i = n - 1; i >= 1; --i) {
        len = 0;
        for(int j = i + 1; j <= n; ++j) if(g[i][j]) valid[++len] = j;
        dfs(1, valid, len);
        ans[i] = answer;
    }
}
int main() {
    scanf("%d%d", &n, &k);
    for(int i = 1; i <= n; ++i)
        for(int j = 1; j <= n; ++j)
            scanf("%d", &g[i][j]);
    MaxClique();
    printf("%d\n",answer);
    return 0;
}

Guess you like

Origin www.cnblogs.com/ucprer/p/12006019.html