time limit per test : 1 second
memory limit per test : 256 megabytes
You are given integer numbers . Consider graph on nodes, in which nodes ≠ are connected if and only if, AND ≠0, where AND denotes the bitwise AND operation.
Find the length of the shortest cycle in this graph or determine that it doesn’t have cycles at all.
Input
The first line contains one integer — number of numbers.
The second line contains integer numbers .
Output
If the graph doesn’t have any cycles, output . Else output the length of the shortest cycle.
Examples
Input
4
3 6 28 9
Output
4
Input
5
5 12 9 16 48
Output
3
Input
4
1 2 4 8
Output
-1
Note
In the first example, the shortest cycle is (9,3,6,28).
In the second example, the shortest cycle is (5,12,9).
The graph has no cycles in the third example.
題意:
給定個數字 ~ ,在,之間有連邊,當且僅當≠且 AND ≠ ,求形成的圖的最小環。
題解:
首先枚舉每一位出現的次數,如果次數大於2,那麼答案就是3
如果沒有出現次數大於2的,那麼將所有位出現次數爲2的位所對應的數字取出(最多120個),然後建圖之後用floyd計算最小環。
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int INF=1999122700;
vector<ll>poc[64];
ll mp[504][504],roc[504][504],a[100004];
int n,cnt;
ll gac[504];
int main(){
memset(mp,0,sizeof(mp));
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%lld",&a[i]);
for(int j=0;j<=60;j++){
if(a[i]&(1LL<<j))poc[j].push_back(i);
}
}
for(int i=0;i<=60;i++){
if(poc[i].size()>=3)return puts("3"),0;
}
for(int i=0;i<=60;i++){
if(poc[i].size()==2){
for(int j=0;j<poc[i].size();j++){
gac[++cnt]=poc[i][j];
}
}
}
sort(gac+1,gac+cnt+1);
cnt=unique(gac+1,gac+cnt+1)-gac-1;
for(int i=1;i<=cnt;i++){
for(int j=1;j<=cnt;j++){
mp[i][j]=INF;
roc[i][j]=INF;
}
}
for(int i=1;i<=cnt;i++){
for(int j=1;j<=cnt;j++){
if(i==j)continue;
if(a[gac[i]]&a[gac[j]]){
mp[i][j]=1;
roc[i][j]=1;
}
}
}
/*
for(int i=1;i<=cnt;i++){
for(int j=1;j<=cnt;j++){
if(mp[i][j]==INF)cout<<" -1";
else cout<<" "<<mp[i][j];
}
cout<<endl;
}
*/
ll ans=INF;
for(int k=1;k<=cnt;k++){
for(int i=1;i<k;i++){
for(int j=i+1;j<k;j++){
ans=min(ans,roc[i][k]+roc[k][j]+mp[i][j]);
}
}
for(int i=1;i<=cnt;i++){
for(int j=1;j<=cnt;j++){
mp[i][j]=min(mp[i][j],mp[i][k]+mp[k][j]);
}
}
}
if(ans==INF)puts("-1");
else printf("%lld\n",ans);
/*
for(int i=1;i<=cnt;i++)cout<<a[gac[i]]<<" ";cout<<endl;
for(int i=1;i<=cnt;i++){
for(int j=1;j<=cnt;j++){
if(mp[i][j]==INF)cout<<" -1";
else cout<<" "<<mp[i][j];
}
cout<<endl;
}
*/
return 0;
}