Sample Input
Input
5 4
1 2
2 3
1 4
4 3
Output
1
Input
4 12
1 2
1 3
1 4
2 1
2 3
2 4
3 1
3 2
3 4
4 1
4 2
4 3
Output
12
题意:有向图,找存在几个这样的菱形。
思路:直接遍历每个点a,把这些点当做原始点,将a能直接到达的点放到队列里面,然后在找这些点能到达的点(除a以外,这些点就是a能两步到达的点),用个数组把这些个数记录下来,在其中找b,d即可。例如:数组中记录的数为n,在n中任取两个(b,d),就是C(n,2),就是(n)*(n-1)/2.
#include <algorithm>
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <sstream>
#include <cstdio>
#include <vector>
#include <string>
#include <cmath>
#include <stack>
#include <queue>
#include <deque>
#include <map>
#include <set>
#define MAX 0x3f3f3f3f
using namespace std;
typedef long long ll;
const double PI = acos(-1);
const int M=3e3+10;
#define inf 0x3f3f3f
vector <int> v[M];
queue <int> dq;
int a[M][M];
int n,m;
int sum[M];
int DFS(int x)
{
int i;
memset(sum,0,sizeof(sum));
for(i=0;i<v[x].size();i++)
{
dq.push(v[x][i]);
}
while(!dq.empty())
{
int t=dq.front();
dq.pop();
for(i=0;i<v[t].size();i++)
{
if(v[t][i]!=x)
sum[v[t][i]]++;
}
}
int ans=0;
for(i=1;i<=n;i++)
{
ans+=(sum[i])*(sum[i]-1)/2;
}
return ans;
}
int main()
{
int i,a,b,ans=0;
cin>>n>>m;
for(i=0;i<m;i++)
{
cin>>a>>b;
v[a].push_back(b);
}
for(i=1;i<=n;i++)
ans+=DFS(i);
cout<<ans<<endl;
return 0;
}