通知小弟

目录

         思路1:强连通缩点,与https://ac.nowcoder.com/acm/problem/15707类似。

思路2:DFS加去重。 

思路3:贪心+DFS,入度为零的点一定是需要联系,再遍历其他点,最后判断是否都能联系上。

思路4:并查集求父节点。如果遍历了m个点后每个点都能到达,那么每个父节点也都能到达,可以同理为从父节点向下遍历,那么父节点的个数就是答案。


链接:https://ac.nowcoder.com/acm/problem/15120
来源:牛客网

时间限制:C/C++ 1秒,其他语言2秒
空间限制:C/C++ 32768K,其他语言65536K
64bit IO Format: %lld

题目描述

        在战争时期,A国派出了许多间谍到其他国家去收集情报。因为间谍需要隐秘自己的身份,所以他们之间只是单向联系。所以,某个间谍只能单向联系到一部分的间谍。同时,间谍也不知道跟他联系的是谁。
HA是间谍们的老大,但他也只能联系到部分的间谍。HA现在有一项命令有告诉所有的间谍。HA想要知道他至少要告诉多少个他能联系上的间谍才能通知到所有的间谍。

输入描述:

有多个测试数据。
对于每个测试数据:
第一行为一个整数n,m(0

输出描述:

输出一行,此行中有一个整数,代表HA至少需要联系的间谍数。如果HA不能通知到所有间谍,输出-1。

示例1

输入

3 2
1 2
1 2
1 1
0

输出

-1

示例2

输入

3 1
1
2 2 3
0
0

输出

1

思路1:强连通缩点,与https://ac.nowcoder.com/acm/problem/15707类似。

#include
#include
#include
#include

using namespace std;

const int N = 1000;

int n,m;
int vis[N];
int low[N];
int dfn[N];
stacks;
vectorv[N];
int num[N];
int ans;
int tim;
int sign[N];
int cnt;
int tem[N];
int in[N];
vector rul;

void targan(int x)
{
	low[x] = dfn[x] = ++tim;
	s.push(x);
	vis[x] = 1;
	for(int i=0; i>n>>m;
	for(int i=0; i>num[i];
	for(int i=1; i<=n; i++)
	{
		int a;
		cin>>a;
		for(int j=0; j>b;
			v[i].push_back(b);
		}
	}
	for(int i=0; i

思路2:DFS加去重。 

#include
#include
#include
#include

using namespace std;

const int N = 1000;

int n,m;
vector v[N];
int num[N];
int ans;
int rul[N];
int vis[N];

void dfs(int x,int y)
{
	vis[x] = 1;
	for(int i=0; i>n>>m;
	for(int i=0; i>num[i];
	for(int i=1; i<=n; i++)
	{
		int a;
		cin>>a;
		for(int j=0; j>b;
			v[i].push_back(b);
		}
	}
	for(int i=0; i

思路3:贪心+DFS,入度为零的点一定是需要联系,再遍历其他点,最后判断是否都能联系上。

#include
#include
#include
#include
 
using namespace std;
 
const int N = 1000;
 
int n,m;
vector v[N];
int num[N];
int ans;
vector rul;
int vis[N];
int in[N];
 
void dfs(int x)
{
	vis[x] = 1;
	for(int i=0; i>n>>m;
	for(int i=0; i>num[i];
	for(int i=1; i<=n; i++)
	{
		int a;
		cin>>a;
		for(int j=0; j>b;
			v[i].push_back(b);
			in[b]++;
		}
	}
	for(int i=1; i<=m; i++)
	{
		if(!in[i]) rul.push_back(i);
	}
	for(int i=0; i

思路4:并查集求父节点。如果遍历了m个点后每个点都能到达,那么每个父节点也都能到达,可以同理为从父节点向下遍历,那么父节点的个数就是答案。

#include
#include
#include
#include
 
using namespace std;
 
const int N = 1000;
 
int n,m;
vector v[N];
int num[N];
int ans;
int vis[N];
int pre[N];

int findpre(int x)
{
	return pre[x] == x ? x : (pre[x] = findpre(pre[x]));
}
 
 
void dfs(int x)
{
	vis[x] = 1;
	for(int i=0; i>n>>m;
	for(int i=1; i<=n; i++) pre[i] = i;
	for(int i=0; i>num[i];
	for(int i=1; i<=n; i++)
	{
		int a;
		cin>>a;
		for(int j=0; j>b;
			v[i].push_back(b);
			int x = findpre(i);
			int y = findpre(b);
			pre[y] = x;
		}
	}
	for(int i=0; i

 

你可能感兴趣的:(targan)