• 21.10.28模拟 C


    给定一个图,问这个图能把所有点分成若干个集合,使得有边相连的两点所在集合编号是相邻的

    显然,如果图只有是二分图才有解。图的最长链(两点之间最短路径的最长长度)的长度+1就是最多集合数

    对于直径中衍生的边,可以直接划分到直径中的集合,由于直径的特性,该满足衍生边的所集合数量一定不会超过直径中能够提供的集合数量。

    int vis[N], d[N], st, ans;
    std::queue<int>q;
    int color[N];
    int rr,tt;
    inline void bfs(int sx) {
    	q.push(sx);
    	d[sx] = 0;
    	vis[sx] = st;
    	while(q.size()) {
    		int y(q.front());
    		q.pop();
    		rep(i, 1, n) {
    			if(!a[i][y] || vis[i] == st) continue;
    			vis[i] = st;
    			d[i] = d[y] + 1;
    			q.push(i);
    			if(d[i]>ans){
    				rr=sx;tt=i;
    				ans=d[i];
    			}
    		}
    	}
    }
    int main() {
    	freopen("c.in", "r", stdin);
    	freopen("c.out", "w", stdout);
    	cin >> n;
    	char ch;
    	rep(i, 1, n) {
    		rep(j, 1, n) {
    			cin >> ch;
    			if(ch == '1') {
    			a[i][j] = a[j][i] = 1;
    			}
    		}
    	}
    	memset(color, 0xff, sizeof color);
    	int q[N];
    	rep(i, 1, n) {
    		if(!~color[i]) {
    			q[q[0] = 1] = i;
    			color[i] = 0;
    			rep(kkk, 1, q[0]) {
    				int x = q[kkk];
    				rep(y,1,n) {
    					if(!a[x][y]) continue;
    					if(~color[y] && color[y] != (color[x] ^ 1)) {
    						puts("-1");
    						return 0;
    					}
    					if(!~color[y]) {
    						q[++q[0]] = y;
    						color[y] = color[x] ^ 1;
    					}
    				}
    			}
    		}
    	}
    	
    
    	rep(i, 1, n) {
    		st = i;
    		bfs(i);
    	}
    	cout<<ans + 1 << '
    ';
    	return 0;
    }
    

    本文来自博客园,作者:{2519},转载请注明原文链接:https://www.cnblogs.com/QQ2519/p/15479873.html

  • 相关阅读:
    过滤器
    JSTL自定义标签
    EL表达式自定义函数
    和 区别
    JSTL标签
    jsp内置对象
    Java堆、栈和常量池以及相关String的详细讲解(转)
    jsp和servlet学习总结
    JAVA多线程实现的两种方式
    redis示例
  • 原文地址:https://www.cnblogs.com/QQ2519/p/15479873.html
Copyright © 2020-2023  润新知