首页 > 其他分享 >Codeforces Round #298 (Div. 2) - D. Handshakes

Codeforces Round #298 (Div. 2) - D. Handshakes

时间:2022-09-22 17:25:41浏览次数:43  
标签:cnt include int Codeforces st ++ Handshakes Div now

贪心 + 构造

题意

有 \(n(1<=n<=2*10^5)\) 个人,每分钟有一个人进入房间,房间里任意 3 个人可以组队开始工作并一直持续下去,且只要房间里至少有 3 个人,他们就可以在任意时间开始组队工作;每当一个人进来时,会给当前房间里没有在工作的人握手

给出数组 \(a_i\), 表示第 i 个人跟 \(a_i\) 个人握手了,求这 n 个人进入房间的顺序

思路

  1. 下标从 0 开始便于取模

  2. 第 i 个人只可能跟 \(i\equiv j\mod3且j<=i\) 个人握手

  3. 因为任意时刻都可以有 3 个人组队,所以贪心地尽量满足握手次数的多的人,再让当前房间里空闲的人组队

  4. 可以用 multiset 维护,把余数相同的 \(a_i\) 放到同一个 multiset 中

    在第 i 个人进入时,设房间里有 now 个人,如果 st 中存在 now,就让这个人与 now 个人握手;若不存在,则要有人组队才行,找到 st 中比 now 小的最大的数,让其余人都组队

​ 然而 multiset tle on test63。。。可能常数太大了

可以用 set<pair<int, int> > 来代替,存的是 {a[i], i}

​ 这样输出答案时也更方便

代码

#include <iostream>
#include <algorithm>
#include <cstring>
#include <vector>
#include <cmath>
#include <set>
using namespace std;
#define endl "\n"

typedef long long ll;
typedef pair<int, int> PII;

const int N = 2e5 + 10;
int n;
int a[N];
int cnt[3];
int ans[N];
set<PII> st[3];
void solve()
{
	for (int i = 0; i < n; i++)
	{
		st[a[i] % 3].insert(make_pair(a[i], i));
		cnt[a[i] % 3]++;
	}
	if (cnt[0] != (n + 2) / 3 || cnt[1] != (n + 1) / 3 || cnt[2] != n / 3)
	{
		puts("Impossible");
		return;
	}
	int now = 0;
	for (int i = 0; i < n; i++)
	{
		int id = i % 3;
		auto it = st[id].lower_bound(make_pair(now, -1));
		PII c;
		if (it != st[id].end() && it->first == now)
		{
			c = *it;
			ans[i] = c.second + 1;
		}
		else
		{
			if (it == st[id].begin())
			{
				puts("Impossible");
				return;
			}
			it--;
			c = *it;
			ans[i] = c.second + 1;
		}
		st[id].erase(it);
		now = c.first + 1;
	}
	puts("Possible");
	for (int i = 0; i < n; i++)
		printf("%d ", ans[i]);
	puts("");
}
int main()
{
	// ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
	scanf("%d", &n);
	for (int i = 0; i < n; i++)
		scanf("%d", &a[i]);
	solve();
    return 0;
}

标签:cnt,include,int,Codeforces,st,++,Handshakes,Div,now
From: https://www.cnblogs.com/hzy717zsy/p/16720095.html

相关文章

  • Codeforces Round #814
    难得遇上一把CF,结果unr了。AMainakandArray显然最优策略只有三种:选一个\(i\in[1,n-1]\)的\(a_i\)作为\(a_1\);选一个\(i\in[2,n]\)的\(a_i\)作为\(a......
  • Polycarp Writes a String from Memory CodeForces - 1702B
    PolycarpWritesaStringfromMemoryCodeForces-1702B给定大小为n的字符串,至多每3种不同的字母分为一组,最少将字符串分为多少组?Input第一行输入数据包含一个整......
  • Jzzhu and Children CodeForces - 450A
    JzzhuandChildrenCodeForces-450A有n个孩子在老师的学校上学。老师决定给这些孩子一些苹果。让我们将所有孩子编号为1到n。第i个孩子想要获得至少ai的苹果......
  • CodeForces-189A Cut Ribbon-必须装满的背包
    题意:给定n,s.t. a1*x1+a2*x2+a3*x3=n(1)max:x1+x2+x3对比完全背包,(1)式取等号而不是<=这个差别影响了我们的结果比如:n=7,a1=a2=5,a3=2如果按照完全背包的转移:则在dp[7......
  • CSS带小三角形的div框
    效果图:<spanclass="hint_prompt">超时20天</span>.hint_prompt{border:1pxsolid#fff1f0;border-radius:4px;margin:50px;text-align:center;bor......
  • Codeforces Round #813 (Div. 2) - D. Empty Graph
    构造Problem-D-Codeforces题意给\(n(1<=n<=10^5)\)个点,与权值\(a_i\),这\(n\)个点组成一个完全图,\(a_l\)与\(a_r\)连的边的权值为\(min(a_l,a_{l+1}...a_{r......
  • Codeforces Round #821 (Div. 2) D E
    E首先发现无论何时,每个位置上至多只会有一个球。原因:每个时刻每个球都会移动,所以移动到某个点的时间一定,自然出生时间也一定,显然不可能会有2个点出生时间相同。既然如......
  • Educational Codeforces Round 119 E
    E.ReplacetheNumbers开始想到了一个二分的做法好像是O(nlog)的后来才想了一下可以在两个数组之间反复横跳那我是不是像记忆化搜索一样记录一个路径即可我们记录f[i]......
  • 监听div高度宽度的变化-自定义指令
    上篇内容说到,iframe嵌入其他项目页面,iframe实现自适应高度需要监听div页面高度的变化使用到了局部自定义指定directives:{//使用局部注册指令的方式resize:{//......
  • Codeforces Round #818 (Div. 2) - D. Madoka and The Corruption Scheme
    思维+组合数学Problem-D-Codeforces题意有\(2^n\)个人进行锦标赛,编号1~\(2^n\),每一场输的人失去比赛资格,赢的人继续。Madoka可以选择他们进行的顺序,以及决定哪一......