首页 > 其他分享 >P2419 Cow Contest S

P2419 Cow Contest S

时间:2025-01-18 20:55:00浏览次数:1  
标签:奶牛 return Cow Contest int P2419 leq 编号 include

Cow Contest S

此题链接

题目

FJ的 \(N\)(\(1 \leq N \leq 100\))头奶牛们最近参加了场程序设计竞赛。在赛场上,奶牛们按 \(1, 2, \cdots, N\) 依次编号。每头奶牛的编程能力不尽相同,并且没有哪两头奶牛的水平不相上下,也就是说,奶牛们的编程能力有明确的排名。 整个比赛被分成了若干轮,每一轮是两头指定编号的奶牛的对决。如果编号为 \(A\) 的奶牛的编程能力强于编号为 \(B\) 的奶牛 (\(1 \leq A, B \leq N\),\(A \neq B\)),那么她们的对决中,编号为 \(A\) 的奶牛总是能胜出。 FJ 想知道奶牛们编程能力的具体排名,于是他找来了奶牛们所有 \(M\)(\(1 \leq M \leq 4,500\))轮比赛的结果,希望你能根据这些信息,推断出尽可能多的奶牛的编程能力排名。比赛结果保证不会自相矛盾。

输入

第一行两个用空格隔开的整数 \(N, M\)。

第 \(2\sim M + 1\) 行,每行为两个用空格隔开的整数 \(A, B\) ,描述了参加某一轮比赛的奶牛的编号,以及结果(每行的第一个数的奶牛为胜者)。

输出

输出一行一个整数,表示排名可以确定的奶牛的数目。

样例

5 5
4 3
4 2
3 2
1 2
2 5
2

解释

编号为 \(2\) 的奶牛输给了编号为 \(1, 3, 4\) 的奶牛,也就是说她的水平比这 \(3\) 头奶牛都差。而编号为 \(5\) 的奶牛又输在了她的手下,也就是说,她的水平比编号为 \(5\) 的奶牛强一些。于是,编号为 \(2\) 的奶牛的排名必然为第 \(4\),编号为 \(5\) 的奶牛的水平必然最差。其他 \(3\) 头奶牛的排名仍无法确定。

法一 : dfs

思路

确定一头牛的位置,即要知道前面有\(a\)头牛,后面有(n - a - 1)头牛
用两个图来存,一个图\(gw\)存放所有获胜过的牛,另一个图\(gl\)存放所有失败过的牛

  • 依次dfs得到比x强的牛,比x强的牛还要强的牛.....记录个数sw
  • 依次dfs得到比x弱的牛,比x弱的牛还要弱的牛.....记录个数sl

如果\(sw + sl == n - 1\),则\(cnt++\)

代码

点击
#include <iostream>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <string>
#include <stack>
#include <queue>
#include <unordered_map>
#include <map>
#include <vector>
#include <cstring>
#include <bitset>

using namespace std;
using ll = long long;
const int N = 5e3;
int n, m, sw, sl, stw[N], stl[N];
vector<int> gw[N], gl[N];

int gcd(int a, int b)
{
	if(b == 0) return a;
	else return gcd(b, a % b);
}
bool cmp(int a, int b) {return a > b;}

void dfsw(int x) { //dfs所有比x强的来得到sw
	for(int u : gw[x]) {
		if(!stw[u]) { //如果之前的递归中u没有出现过,则多了一个比x强的
			sw++;
			stw[u] = 1;
			dfsw(u); //看有没有比u强的。u比x强,即比u强的也比x强
		}
	}
}

void dfsl(int x) { //dfs所有比x弱的来得到sl
	for(int u : gl[x]) {
		if(!stl[u]) {
			sl++;
			stl[u] = 1;
			dfsl(u);
		}
	}
}

int main()
{
	ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
	cin >> n >> m;
	int cnt = 0;
	for(int i = 0; i < m; i++) {
		int a, b; cin >> a >> b;
		gw[b].push_back(a); //记录相对于b的所有胜者
		gl[a].push_back(b); //记录相对于a的所有败者
	}
	for(int i = 1; i <= n; i++) {
		sw = 0, sl = 0; //sw比i强的, sl是比i弱的
		memset(stw, 0, sizeof stw);
		memset(stl, 0, sizeof stl);
		dfsw(i), dfsl(i);
		if(sw + sl == n - 1) cnt++; //如果n-1个位置都能确定,那么成立
	}
	cout << cnt;
}

法二 : floyd

思路

传递闭包 : 通过传递性推断出多个元素之间的关系
如果\(i\) 和 \(j\) 能够建立直接关系\(f[i][j] = 1\) 或者 通过桥梁 \(k\) 建立间接关系 \(f[i][k] = 1 , f[k][j] = 1\), 那么\(i\) 和 $ j$ 之间有关系
如果\(i\) 和 \(n - 1\)个数都有关系,那么符合条件

代码

点击
#include <iostream>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <string>
#include <stack>
#include <queue>
#include <unordered_map>
#include <map>
#include <vector>
#include <cstring>
#include <bitset>

using namespace std;
using ll = long long;
const int N = 110;
int f[N][N], n, m;

int gcd(int a, int b)
{
	if(b == 0) return a;
	else return gcd(b, a % b);
}
bool cmp(int a, int b) {return a > b;}

void solve() {
	int n, m; cin >> n >> m;
	for(int i = 0; i < m; i++) {
		int a, b; cin >> a >> b;
		f[a][b] = 1;
	}
	for(int k = 1; k <= n; k++) {
		for(int i = 1; i <= n; i++) {
			for(int j = 1; j <= n; j++) 
				f[i][j] |= f[i][k] & f[k][j];
				//如果i和j具有直接输赢i>j, 或者以k作为桥梁i>k>j, 那么i和j能确定输赢关系
		}
	}
	int sum = 0;
	for(int i = 1; i <= n; i++) {
		int cnt = 1; //cnt为是否能建立关系
		for(int j = 1; j <= n; j++) 
		//自己和自己不用管, 所以i != j时
			if(i != j) cnt = cnt & (f[i][j] | f[j][i]);
			//遍历所有点, 看是否除i以外的点都和i有关系
			//如果有一个i和j无关, 那么cnt = 0, 后面循环的cnt则都为0
		sum += cnt; //如果i能做到, sum自增
	}
	cout << sum;
}

int main()
{
	ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
	solve();
}

标签:奶牛,return,Cow,Contest,int,P2419,leq,编号,include
From: https://www.cnblogs.com/PeachyGalaxy/p/18678852/0118p

相关文章

  • CF 284B.Cows and Poker Game(Java实现)
    题目分析    奶牛也打扑克。一共有三种情况,简称AFI,并且只有自己为AI状态其余全部人为AF状态才可以亮手牌。思路分析    根据题目分析,针对三个不同状态分析情况:当且仅当有一个I时,唯有这个奶牛可以亮牌,如果I的个数大于1,一个也不能亮牌;当没有I时,判断A的个数,有......
  • AtCoder Beginner Contest 388
    A-A-?UPC题意给定字符串\(s\),输出\(s\)首个字符与\(UPC\)组成的字符串思路模拟代码点击查看代码#include<bits/stdc++.h>usingnamespacestd;#defineintlonglongtypedefpair<int,int>pii;constintmxn=1e6+5;voidsolve(){ strings; ci......
  • 内存管理优化技术:写时复制(Copy-On-Write, COW)
    文章目录说明写时复制(Copy-On-Write,COW)概念一写时复制的工作原理二为什么需要写时复制三COW在fork()中的应用四COW的优势五COW的应用场景六COW的局限性和挑战七总结说明本文是针对个人专业知识查缺补漏,结合大模型对话内容整理而来,请辩证看待文章!写时......
  • AtCoder Regular Contest 058 [ARC058] F - Unhappy Hacking
    题意:有三种操作,在右边添加0/1或删除最右边的数(空字符串无操作)给出操作数\(N\),字符串\(s\),问有多少种方法经过\(N\)次操作后得到字符串\(S\)思路最开始在想三维dp,虽然发现了性质,但是没想到很好的用法重要性质:答案与字符串内容无关,仅与字符串长度有关定义\(f_{i,j}\)为操作\(i......
  • VP AtCoder Beginner Contest 382
    A-DailyCookie题意:有\(n\)个盒子,有些盒子有蛋糕,被人吃了\(m\)个蛋糕,问有几个盒子没蛋糕。直接计算即可。点击查看代码voidsolve(){intn,m;std::cin>>n>>m;std::strings;std::cin>>s;std::cout<<n-std::count(s.begin(),s.end(),......
  • AtCoder Regular Contest 058 [ARC058] E - Iroha and Haiku
    题意:对于所有长度为\(n\),每个数在1到10之间的序列,问有多少个中包含一字串,满足字串可以分为三段和恰好为\(x,y,z\)的部分数据满足:\[3\len\le40,1\lex\le5,1\ley\le7,1\lez\le5,\]思路正向统计有多少个序列满足会遇到重复统计的问题,难以克服,考虑统计统......
  • VP Daiwa Securities Co. Ltd. Programming Contest 2024(AtCoder Beginner Contest 38
    A-Humidifier1题意:一个漏水的桶,在零时刻有零升水,进行\(n\)次加水,在\(t_i\)时刻加\(v_i\)升水,每一时刻会漏一生水,问第n次加水后有多少升水。直接模拟即可,每次加水先减去漏掉的水,注意至少有0升,然后加上新加的水。点击查看代码voidsolve(){intn;std::cin>>n;......
  • VP Toyota Programming Contest 2024#12(AtCoder Beginner Contest 384)
    A-aaaadaa题意:给你一个字符串和两个字符\(c_1\),\(c_2\),把字符串里的所有不等于\(c_1\)的字符都换成\(c_2\)。模拟即可。点击查看代码voidsolve(){intn;chara,b;std::cin>>n>>a>>b;std::strings;std::cin>>s;for(auto&c:......
  • AtCoder Regular Contest 067
    \(AT\_arc067\_a\)https://www.luogu.com.cn/problem/AT_arc067_a题解:筛出\(1\simn\)中质数,计算每个质数出现次数,再累乘即可。#include<bits/stdc++.h>usingnamespacestd;typedeflonglongLL;constintN=1010,P=1e9+7;intn;intbuc[N];intprime[N],cnt;bool......
  • AtCoder Regular Contest 066(缺d)
    \(AT\_arc066\_a\)https://www.luogu.com.cn/problem/AT_arc066_a题解:长度为\(n\)的队列,其\(A\)数组固定,直接判断题目给定\(A\)数组是否符合题意即可。若符合题意,答案为\(2^{\frac{n}{2}}\),否则答案为\(0\)。#include<bits/stdc++.h>usingnamespacestd;typedeflonglon......