首页 > 其他分享 >Codeforces Global Round 27

Codeforces Global Round 27

时间:2024-11-07 19:59:51浏览次数:1  
标签:CI 27 const int Global Codeforces include RI define

Preface

这场其实是上周六 VP 的,但因为后面连着好几天组队训练就一直没补题,拖到今天才补

这场VP 的时候写了 A~E,F 感觉会了但是急着吃饭就跑了,今天写了下 F 发现贼好写写完就过了,亏麻了


A. Sliding

签到,手玩下式子即可

#include<cstdio>
#include<iostream>
#define int long long
#define RI register int
#define CI const int&
using namespace std;
int t,n,m,r,c;
signed main()
{
	for (scanf("%d",&t);t;--t)
	{
		scanf("%lld%lld%lld%lld",&n,&m,&r,&c);
		printf("%lld\n",(n-r)*m+(m-c)+(n-r)*(m-1));
	}
	return 0;
}

B. Everyone Loves Tres

看一眼好怪啊不会做,想了会无果索性直接打表找到规律

当 \(n\) 为偶数时答案形如 \(3333\dots33366\);当 \(n\) 为奇数时答案形如 \(3333\dots36366\)

#include<cstdio>
#include<iostream>
#include<vector>
#include<algorithm>
#define int long long
#define RI register int
#define CI const int&
using namespace std;
const int LIM=18;
vector <int> vec[25];
int t,n;
inline void DFS(CI now=0,CI sum=0)
{
	if (now>LIM) return;
	if (sum!=0&&sum%66==0) vec[now].push_back(sum);
	DFS(now+1,sum*10+3); DFS(now+1,sum*10+6);
}
signed main()
{
//	DFS(); for (RI i=1;i<=LIM;++i)
//	if (!vec[i].empty()) printf("%lld\n",*min_element(vec[i].begin(),vec[i].end()));
	for (scanf("%lld",&t);t;--t)
	{
		scanf("%lld",&n);
		if (n==1||n==3) { puts("-1"); continue; }
		if (n%2==0)
		{
			for (RI i=1;i<=n-2;++i) putchar('3');
			puts("66");
		} else
		{
			for (RI i=1;i<=n-5;++i) putchar('3');
			puts("36366");
		}
	}
	return 0;
}

C. Alya and Permutation

很神秘的构造啊,先考虑 \(n\) 为偶数的情形,令 \(k\) 为 \(n\) 二进制下的最高位

不难发现 \(2^{k+1}-1\) 是答案是上界,下面给出一种方法构造出这个上界

先将 \(1,2,3,4,7,8,2^k-1,2^k\) 放在序列最后,然后前面的奇数位置放剩下的偶数,偶数位置放剩下的奇数即可

不难发现此时前面一波操作后会得到一个 \(1\),然后进入上面的序列后最终就会得到 \(2^{k+1}-1\)

当 \(n\) 为奇数时显然 \(n\) 就是答案的上界,因此把 \(1\sim n-1\) 用上述方法构造后,把 \(n\) 放在末尾即可

注意这个做法当且仅当 \(n=5\) 时需要特判一下

#include<cstdio>
#include<iostream>
#include<vector>
#include<algorithm>
#define RI register int
#define CI const int&
using namespace std;
int t,n;
signed main()
{
	for (scanf("%d",&t);t;--t)
	{
		scanf("%d",&n); vector <int> ans;
		auto solve=[&](CI n)
		{
			vector <int> vec;
			auto check=[&](CI x)
			{
				return (x&(-x))==x;
			};
			for (RI i=n;i>=1;--i)
			{
				if (check(i)||check(i+1)) continue;
				vec.push_back(i);
			}
			for (RI i=1;i<=n;++i)
			if (check(i)||check(i+1)) vec.push_back(i);
			return vec;
		};
		if (n==5) ans={2,1,3,4,5};
		else if (n%2==0) ans=solve(n);
		else ans=solve(n-1),ans.push_back(n);
		int ret=0; for (RI i=0;i<ans.size();++i)
		if (i&1) ret|=ans[i]; else ret&=ans[i];
		printf("%d\n",ret);
		for (auto x:ans) printf("%d ",x); putchar('\n');
	}
	return 0;
}

D. Yet Another Real Number Problem

先考虑一个无视数的规模时的做法,这个就很经典

拿一个递减的单调栈维护所有还可以往后操作的数,每次考虑如果把栈顶数中的 \(2\) 都换给当前数是否更优,是则弹栈

但直接做数的规模会变得不可控,因此很容易想到把每个数是 \(2\) 的多少次幂以及剩余部分开个结构体存起来

手玩一下比较的式子会发现可以推出十分简单的表达式,然后这题就做完了

#include<cstdio>
#include<iostream>
#include<vector>
#include<algorithm>
#define RI register int
#define CI const int&
using namespace std;
const int N=200005,mod=1e9+7;
inline int quick_pow(int x,int p=mod-2,int mul=1)
{
	for (;p;p>>=1,x=1LL*x*x%mod) if (p&1) mul=1LL*mul*x%mod; return mul;
}
inline void inc(int& x,CI y)
{
	if ((x+=y)>=mod) x-=mod;
}
inline void dec(int& x,CI y)
{
	if ((x-=y)<0) x+=mod;
}
struct ifo
{
	int val,p;
	inline ifo(CI VAL=0,CI P=0)
	{
		val=VAL; p=P;
	}
	inline int rval(void)
	{
		return 1LL*val*quick_pow(2,p)%mod;
	}
	friend inline bool operator < (const ifo& A,const ifo& B)
	{
		if (B.p>=30) return 1;
		return 1LL*A.val<1LL*B.val*(1LL<<B.p);
	}
}stk[N]; int t,n;
signed main()
{
	for (scanf("%d",&t);t;--t)
	{
		scanf("%d",&n); int top=0,ans=0;
		for (RI i=1;i<=n;++i)
		{
			ifo cur; scanf("%d",&cur.val);
			while (cur.val%2==0) ++cur.p,cur.val/=2;
			while (top&&stk[top]<cur)
			{
				dec(ans,stk[top].rval());
				cur.p+=stk[top].p; stk[top].p=0;
				inc(ans,stk[top--].rval());
			}
			stk[++top]=cur; inc(ans,cur.rval());
			printf("%d%c",ans," \n"[i==n]);
		}
	}
	return 0;
}

E. Monster

考虑令 \(f(i,j)\) 表示进行 \(i\) 次一操作,\(j\) 次二操作最多能打多少血,显然存在最优策略

即先进行 \(k\) 次一操作,\(1\) 次二操作的循环,一直到一操作用完,然后把剩下的二操作用完

则很容易推出 \(s=\min(\lfloor\frac{i}{k}\rfloor,j),f(i,j)=k\times \frac{s\times (s+1)}{2}+i\times (j-s)\)

观察这个式子会发现 \(f(i,j)\ge \frac{i\times j}{2}\),在 \(j=\lfloor\frac{i}{k}\rfloor\) 取等号,因此我们可以推出 \(\min(i,j)\le \sqrt {2z}\)

直接枚举其中的一个然后二分另一个即可,单组数据复杂度 \(O(\sqrt z\log z)\)

#include<cstdio>
#include<iostream>
#include<vector>
#include<algorithm>
#define int long long
#define RI register int
#define CI const int&
using namespace std;
const int LIM=2e4;
int t,x,y,z,k;
signed main()
{
	for (scanf("%lld",&t);t;--t)
	{
		scanf("%lld%lld%lld%lld",&x,&y,&z,&k);
		auto calc=[&](CI mxd,CI num)
		{
			int tmp=min(num,mxd/k);
			return (tmp+1)*tmp/2LL*k+mxd*(num-tmp);
		};
		int ans=1e18;
		for (RI i=1;i<=LIM;++i)
		{
			int l=1,r=z,mid,ret=-1;
			while (l<=r) if (calc(i,mid=l+r>>1)>=z) ret=mid,r=mid-1; else l=mid+1;
			if (ret!=-1) ans=min(ans,i*x+ret*y);
		}
		for (RI i=1;i<=LIM;++i)
		{
			int l=1,r=z,mid,ret=-1;
			while (l<=r) if (calc(mid=l+r>>1,i)>=z) ret=mid,r=mid-1; else l=mid+1;
			if (ret!=-1) ans=min(ans,ret*x+i*y);
		}
		printf("%lld\n",ans);
	}
	return 0;
}

F. Tree Operations

考虑当总操作次数固定时该怎么做,显然此时可以求出每个点操作的次数 \(c_i\)

不妨 DP 求解,令 \(f_i\) 表示处理完点 \(i\) 的子树后还需要上面进行多少次操作,首先有 \(f_u=a_u+\sum_{u\to v} f_v\),然后分情况讨论:

  • \(c_i\le f_i\),此时直接令 \(f_i=f_i-c_i\) 即可,剩余的操作由祖先节点补上;
  • \(c_i>f_i\),此时多出的 \(c_i-f_i\) 次操作可以在一个点上重复加减消耗,因此 \(f_i=(c_i-f_i)\bmod 2\);

但直接枚举操作次数也不现实,而直接对总操作次数二分也没有单调性

不过我们可以注意到,若 \(m\) 是一个合法的解,则 \(m+2n\) 也一定合法,因为我们至少可以通过在每个点处都加减抵消来达到相同的结果

因此这题直接枚举总操作次数对 \(2n\) 取模的结果,剩下的部分就有二分性了,总复杂度 \(O(n^2\log n)\)

#include<cstdio>
#include<iostream>
#include<vector>
#define int long long
#define RI register int
#define CI const int&
using namespace std;
const int N=2005;
int t,n,rt,a[N],f[N]; vector <int> v[N];
inline void DP(CI now,CI lim,CI fa=0)
{
	int cnt=lim/n+(now<=lim%n); f[now]=a[now];
	for (auto to:v[now]) if (to!=fa) DP(to,lim,now),f[now]+=f[to];
	if (f[now]>=cnt) f[now]-=cnt; else f[now]=(cnt-f[now])%2;
}
signed main()
{
	for (scanf("%lld",&t);t;--t)
	{
		scanf("%lld%lld",&n,&rt);
		for (RI i=1;i<=n;++i) scanf("%lld",&a[i]),v[i].clear();
		for (RI i=1;i<n;++i)
		{
			int x,y; scanf("%lld%lld",&x,&y);
			v[x].push_back(y); v[y].push_back(x);
		}
		int ans=1e18;
		for (RI m=0;m<2LL*n;++m)
		{
			int l=0,r=2e9,mid,ret=-1;
			while (l<=r)
			{
				mid=l+r>>1; DP(rt,2LL*n*mid+m);
				if (f[rt]==0) ret=mid,r=mid-1; else l=mid+1;
			}
			if (ret!=-1) ans=min(ans,2LL*n*ret+m);
		}
		printf("%lld\n",ans);
	}
	return 0;
}

Postscript

最近比赛压力增大,而且也有几门课要期中考/期末考,同时某人的炉石瘾也越来越大了

但不管怎么说还是不能懈怠了训练啊

标签:CI,27,const,int,Global,Codeforces,include,RI,define
From: https://www.cnblogs.com/cjjsb/p/18533864

相关文章

  • Java - 27 final
    Java-27final可以修饰类、属性、方法和局部变量使用场景不希望类被继承不希望父类的某个方法被子类重写不希望类的某个属性被修改(常量)classA{publicfinaldoubleTAX_RATE=0.08;}不希望局部变量被修改(局部常量)细节final修饰的属性在定义时必须赋......
  • Java - 27 抽象类 + 接口
    Java抽象类+接口抽象类当父类的某些方法需要声明,但又不确定如何实现时(父类方法不确定性问题),可以将其声明为抽象方法,这个类就是抽象类publicabstractclassAnimal{abstractpublicvoideat();//抽象方法没有方法体}一般来说,抽象类会被继承,由其子类具体实现细节......
  • Codeforces Round 982 (Div. 2)(A~C)
    对dp还不是特别熟练只做到了C(还是太菜了),开始前刚好各种事情来了,vp晚了10多分钟开才始做题,喜提排名(不是)3000+,后面有时间就尽量把dp补掉A.RectangleArrangement你需要在一个无限的方格网格上涂色,所有格子最初都是白色的。为了完成这项任务,你有\(n\)个印章。每个印章是一个......
  • Nexpose 6.6.277 for Linux & Windows - 漏洞扫描
    Nexpose6.6.277forLinux&Windows-漏洞扫描Rapid7VulnerabilityManagement,releasedNov06,2024请访问原文链接:https://sysin.org/blog/nexpose-6/查看最新版。原创作品,转载请保留出处。作者主页:sysin.org您的本地漏洞扫描程序新增功能2024年11月......
  • 20222327 2024-2025-1 《网络与系统攻防技术》实验四实验报告
    一、实验内容1.恶意代码文件类型标识、脱壳与字符串提取2.使用IDAPro静态或动态分析crackme1.exe与crakeme2.exe,寻找特定输入,使其能够输出成功信息。3.分析一个自制恶意代码样本rada,并撰写报告,回答问题4.取证分析实践二、实验过程1.对恶意代码样本,进行文件类型识别,脱壳与字......
  • LeetCode3270[求出数字答案]
    题目链接LeetCode3270[求出数字答案]详情实例实例1实例2实例3提示题解思路先依次取出num1,num2,num3的每位的位数  取最高位的时候,用数字除以1000,然后取10的余数  取第三位的时候,用数字除以100,然后取10的余数  取第二位的时候,用数字除以10,然后取10的余数......
  • 【51蛋骗鸡16路电子开关编程CD4067使用switch】2021-12-27
    缘由关于单片机矩阵键盘控制16路led-24小时必答区矩阵键值必须配合硬件对应,若矩阵接法不同则键值也不同,取键值可以直接调用矩阵扫描函数,按下按键后看P2输出Q0对应计算器最末位Q7对应第八位,并可发送一个值到P2验证.CD4067为十六路模拟开关,其内部包括一个16选1的译码器和......
  • [luoguP2713] 罗马游戏
    题意原题链接维护一个数据结构,要求支持合并集合或删除集合最小值并输出。sol双倍经验,同[luoguP3377]左偏树/可并堆代码#include<iostream>#include<algorithm>#include<cstring>usingnamespacestd;constintN=1000005;structNode{intl,r;int......
  • CF1270 Good Bye 2019
    Dashboard玩构造玩的,服了。A拥有最大牌的必胜。linkB若相邻的差\(\ge2\)则有解,否则根据变化连续性一定无解。linkC加两个数,第一个数为之前所有数的异或和。加进来之后异或为0。第二个数为加完第一个数之后的和。linkD考虑\(k=n-1\)时,分别询问除去每个数之后的第\(......
  • Educational Codeforces Round 161 (Rated for Div. 2) - VP记录
    Preface先被A题硬控\(20\)分钟,有点不爽。又看到E题AC的人比D题多而去嗑E题去了,结果D题反而是我更能做的。将问题排序:根据你所需付出的努力,将能够最快解决的问题排在前面。(答题的次序为:以前做过的,容易的,不熟悉的,难的)——李博杰《骗分导论》\(\rmP_{114}\)所以......