Shortest Cycle
题意
有n(n <= 100000)个数字,两个数字间取&运算结果大于0的话连一条边。问图中的最小环。
思路
可以发现当非0数的个数很大,比如大于200时,一定存在长度为3的环。
如果小于200, 我们就用到了Floyd求最小环的技巧。
#include <algorithm> #include <iterator> #include <iostream> #include <cstring> #include <cstdlib> #include <iomanip> #include <bitset> #include <cctype> #include <cstdio> #include <string> #include <vector> #include <stack> #include <cmath> #include <queue> #include <list> #include <map> #include <set> #include <cassert> #include <unordered_map> // #include<bits/extc++.h> // using namespace __gnu_pbds; using namespace std; #define pb push_back #define fi first #define se second #define debug(x) cerr<<#x << " := " << x << endl; #define bug cerr<<"-----------------------"<<endl; #define FOR(a, b, c) for(int a = b; a <= c; ++ a) typedef long long ll; typedef unsigned long long ull; typedef long double ld; typedef pair<int, int> pii; typedef pair<ll, ll> pll; const int inf = 0x3f3f3f3f; const ll inff = 0x3f3f3f3f3f3f3f3f; const int mod = 998244353; template<typename T> inline T read(T&x){ x=0;int f=0;char ch=getchar(); while (ch<'0'||ch>'9') f|=(ch=='-'),ch=getchar(); while (ch>='0'&&ch<='9') x=x*10+ch-'0',ch=getchar(); return x=f?-x:x; } /**********showtime************/ const int maxn = 2e5+9; ll a[maxn]; int cnt[20]; ll ans; ll dp[209][209], g[209][209]; vector<ll>b; int main(){ int n; scanf("%d", &n); int cnt = 0; for(int i=1; i<=n; i++){ scanf("%lld", &a[i]); if(a[i] == 0) cnt++; else b.pb(a[i]); } if(n - cnt > 200) puts("3"); else { int n = b.size(); for(int i=1; i<=n; i++){ for(int j=1; j<=n; j++) { if(i == j) dp[i][j] = 0,g[i][j] = 0; else dp[i][j] = dp[j][i] = inf, g[i][j] = inf; } } for(int i=0; i<n; i++) { for(int j=i+1; j<n; j++) { if((b[i] & b[j]) > 0) { dp[i+1][j+1] = 1; dp[j+1][i+1] = 1; g[i+1][j+1] = 1; g[j+1][i+1] = 1; } } } ans = inf; for(int k=1; k<=n; k++) { for(int i=1; i<k; i++) { for(int j=i+1; j<k; j++) { ans = min(ans, dp[i][j] + g[k][i] + g[k][j]); } } for(int i=1; i<=n; i++) { for(int j=1; j<=n; j++) { dp[i][j] = min(dp[i][j], dp[i][k] + dp[k][j]); } } } if(ans == inf) puts("-1"); else printf("%lld ", ans); } return 0; }