首页 > 其他分享 >2024牛客多校3J Rigged Games

2024牛客多校3J Rigged Games

时间:2024-07-24 13:53:30浏览次数:7  
标签:dots cnt 比赛 int 多校 2024 3J cnt0 获胜

欢迎来我的博客看这篇题解

Problem

在两人竞技比赛中,对于任何正整数 \(a\) ,我们定义 \(BO(2 a-1)\) 如下:两名玩家继续竞争,直到其中一人获胜 \(a\) 次,那么他赢得整个比赛。\(BO(2 a-1)\) 最多包含 \(2a-1\) 小局游戏,最少包含 \(a\) 小局游戏。

现在两个人进行一场 DotA2 比赛,使用的是 \(BO(2b-1)\ \texttt{of}\ BO(2a-1)\) 赛制。该赛制由最多 \(2b-1\) 最少 \(b\) 场主要比赛组成,每个主要比赛都是一个 \(BO(2a-1)\),由最多 \(2a-1\) 最少 \(a\) 局次要比赛组成。

假如比赛的结果是预先确定的:有一个长度为 \(n\) 的 \(0-1\) 串 \(T\) ,其中 1 表示 A 获胜,0 表示 B 获胜。A 和 B 的每一局次要游戏结果都从串 \(T\) 中获取。假如从 \(T\) 串的每个位置开始重复获取次要游戏结果,求最后谁赢了?

\(1\le n,a,b\le 10^5\)

Example

7 2 2
1010101

在该样例中,每个主要比赛都是 \(BO3\),也就是 3 局 2 胜制。主要比赛的每个次要比赛也是 \(BO3\)。现在需要看看从这 7 个位置开始获取每场次要比赛的结果,先求得每场主要比赛的结果,再求整场比赛谁获胜。

从第一个位置开始比赛,\(T=1010101|1010101\dots\),次要比赛的结果为 1:2 2:1 0:2 2:1 1:2... 即 \(10101|10101\dots\),主要比赛的结果为 1:2 1:2...,即 \(00\dots\),也就是 A 队将以 2:1获胜,结果为 \(1\)。

从第二个位置开始比赛,\(T=0101011|0101011\dots\),次要比赛的结果为 \(01101|01101\dots\),主要比赛结果为 \(101\dots\) 也就是 A 队将以 2:1 获胜,结果为 \(1\).

继续从第三个位置开始比赛……直到从最后一个位置开始比赛。得到最终结果为 \(1110111\)。

Solution

将问题简化为这样的形式:

将循环串 \(T\) 以如下规则生成新循环串 \(T^\prime\):

将串 \(T\) 展开。按照顺序在 \(T\) 上进行游戏。如果数字 \(0\)(或数字 \(1\))的累计数量等于胜利条件 \(a\) ,则该小局的胜利方为 \(0\)(或 \(1\)),立即结束该小局游戏并开始新局。在这样生成的“胜利0-1串”上重复上述的游戏规则,当某个数字的累计数量等于胜利条件 \(b\),则该大局结束,得到大局的胜利方。

稍微写点模拟代码演示:

for(int x=1;x<=n;x++)
{
	int y=x;
    int cnt[2]={0,0};
    cnt[T[x]]++;
    while(1)
    {
        if(cnt[0]>=a||cnt[1]>=a)// or >=b
        {
            if(cnt[0]>=b) cout<<0;
            else cout<<1;
            break;
		}
        y++;
        if(y>n) y-=n;
        cnt[T[y]]++;
    }
}

这是一个嵌套问题。我们先考虑内层问题。

注意到上述代码中的 y 只会向右循环移动,可以用循环双指针在 \(O(n)\) 时间复杂度内解决内层问题。

我们可以得到:在 \(x\) 处开始进行一个小局,游戏结束时获胜方为谁、结束之后下一个小局从哪里开始进行。

但是从小局的胜利情况推大局的胜利情况就不能用双指针如法炮制了。因为此时面对的不是一个循环串 \(T\),而是一个内向基环树森林,我们需要将每个点作为起点跑双指针,这样会超时的。

考虑倍增。

我们定义 \(jump_{x,k}\) 为从 \(x\) 开始,进行 \(2^k\) 个小局之后,接下来会从何处继续游戏。定义 \(cnt_{x,k,0/1}\) 为从 \(x\) 开始,进行了 \(2^k\) 个小局中,A/B 队获胜的数量。

在上面,我们已经用双指针求出了每一个起点 \(x\) 开始一小局的胜利方(令 \(cnt_{x,0,胜利方}=1\))和下一局的起点 \(jump_{x,0}\)。由此预处理 \(k=1,2,3\dots\) 的情况。

现在对于每个起点 \(x\),我们进行倍增。类似于倍增求 LCA,我们倍增地找到最远的大局结束点 \(y\),使得这之间双方胜利数量都刚好小于 \(b\)。此时,再向后走一步(\(y=jump_{y,0}\))一定会导致这一大局结束,所以接下来的这一小局的获胜方就是从 \(x\) 开始玩一大局的获胜方了。

Code

#define N 100010

int n,a,b;
string s;
int jump[N][31];
LL cnt[N][31][2];
string ans;

int main()
{
	ios::sync_with_stdio(false);
	cin.tie(0);
	cout.tie(0);
	cout.precision(10);
	int t=1;
//	cin>>t;
	while(t--)
	{
		cin>>n>>a>>b;
		cin>>s;
		int l=0,r=0;
		int cnt0[2]={0,0};
		cnt0[s[0]-'0']=1;
		while(1)
		{
			if(l>=s.size()) break;
			if(cnt0[0]>=a||cnt0[1]>=a)
			{
				bool win=(cnt0[1]>=a);
				cnt[l][0][win]=1;
				jump[l][0]=r+1;
				cnt0[s[l]-'0']--;
				l++;
				continue;
			}
			r++;
			if(r>=s.size()) r-=s.size();
			cnt0[s[r]-'0']++;
		}
		
		
//		for(int i=0;i<s.size();i++) cout<<cnt[i][0][0]<<" "<<cnt[i][0][1]<<endl;
		
		for(int k=1;k<=30;k++)
		{
			for(int i=0;i<s.size();i++)
			{
				jump[i][k]=jump[jump[i][k-1]][k-1];
				cnt[i][k][0]=cnt[i][k-1][0]+cnt[jump[i][k-1]][k-1][0];
				cnt[i][k][1]=cnt[i][k-1][1]+cnt[jump[i][k-1]][k-1][1];
			}
		}
		
		
		for(int i=0;i<s.size();i++)
		{
			int x=i;
			int now[2]={0,0};
			for(int k=30;k>=0;k--)
			{
				if(now[0]+cnt[x][k][0]<b&&now[1]+cnt[x][k][1]<b)
				{
					now[0]+=cnt[x][k][0];
					now[1]+=cnt[x][k][1];
					x=jump[x][k];
				}
			}
			ans.push_back(cnt[x][0][1]+'0');
//			if(now[0]==b) ans.push_back('0');
//			if(now[1]==b) ans.push_back('1');
		}
		
		cout<<ans<<endl;
		
	}
	return 0;
}

标签:dots,cnt,比赛,int,多校,2024,3J,cnt0,获胜
From: https://www.cnblogs.com/Vanilla-chan/p/18320736

相关文章

  • 2024/7/12
    //考试时间分配及感想T1聂赫柳朵夫之变link:T1score:100time:1h题型及难点:我都能A可见这题有多简单.jpgT2夏目漱石之月link:T2score:0time:90min题型及难点:1.没有大样例,所以对题目的分析尤其是读题有极高的要求(说不定就栽在哪里了(=@__@=))解题思路60pts首......
  • 2024年5款VSCode实用扩展推荐
    1.GitHubCopilot扩展说明:您可以在VisualStudioCode中使用Copilot来生成代码、修复错误、询问有关代码的问题等等。地址:https://marketplace.visualstudio.com/items?itemName=GitHub.copilot2.AIFlowchart2024扩展说明:AIFlowchart它可以帮助您使用Mermaid.js语......
  • 2024暑假集训总结
    2024暑假集训总结知识点清单:树状数组拓展:(1)k维前缀和(2)树状数组+倍增没码过,小慌线段树:(1)线段树不仅仅是一个维护区间和、区间最值或者类似于方差那道题,维护区间的平方等等信息,它的深层是将区间拆分为\(O(logn)\)个子区间从而将修改与查询降为\(O(logn)\)级别,因此对于线......
  • 2024牛客多校第三场
    磨合上升期,爽!B队友做的#include<bits/stdc++.h>usingnamespacestd;#defineintlonglonginlineintread(){intx=0;boolf=1;charch=getchar();for(;ch<'0'||ch>'9';ch=getchar())f^=(ch=='-');for(;ch>=&#......
  • 2024-07-24 想法记录,关于 可以准点睡觉 和 拖延寄快递
    2024-07-24     昨天晚上可以及时睡觉,比原来早,12点以前睡下来,11点半闭上的眼。之前的晚睡,怎么突然在这一会就可以变回来了呢? 我思考了一下,最重要的原因,我看见自己下巴和两鬓的白胡子,白发了。我才人到中年而已,年纪不大就已经头发胡子都变白了,不敢再熬夜了。再仔细感受......
  • 源代码加密软件,2024年企业常用的五款源代码加密软件推荐
    在当今高度数字化和竞争激烈的商业环境中,保护源代码的安全性对于企业来说至关重要。源代码不仅是企业的核心资产,也是创新和竞争优势的关键所在。一旦源代码泄露,可能导致知识产权的丧失、商业机密的暴露,甚至对企业的声誉造成不可挽回的损害。因此,选择一款可靠的源代码加密软件......
  • 2024 暑假集训
    树状数组&线段树线段树合并,主席树等知识点是第一次接触。同时对扫描线能解决的问题有了些更好的认知。毕竟是之前学过的东西,还是比较好的。掌握程度:\(85\%^+\)离线分治算法具体是:线段树分治\(80\%^+\)就是个线段树上二分。CDQ分治基于时间的分治\(75\%^+\)基本......
  • 【稳定检索|投稿优惠】2024年金融创新与当代贸易国际会议(ICFICT 2024)
    2024年金融创新与当代贸易国际会议2024InternationalConferenceonFinancialInnovationandContemporaryTrade【1】大会信息会议名称:2024年金融创新与当代贸易国际会议会议简称:ICFICT2024大会时间:请查看官网大会地点:中国·南京截稿时间:请查看官网审稿通知:投稿......
  • 213java jsp SSM疫情期间高校师生外出请假管理系统(源码+文档+开题+任务书+运行视频+讲
     项目技术:SSM+Maven+Vue等等组成,B/S模式+Maven管理等等。环境需要1.运行环境:最好是javajdk1.8,我们在这个平台上运行的。其他版本理论上也可以。2.IDE环境:IDEA,Eclipse,Myeclipse都可以。推荐IDEA;3.tomcat环境:Tomcat7.x,8.x,9.x版本均可4.硬件环境:windows7/8/1......
  • [2024JZYZ暑期集训]知识点总结
    前言第三次暑期集训了,与前两次不同,这次没有前两次的激动了,所以也能够更深入地学习算法。闲话宿舍挺好,有空床能住。捡了三块钱,史上最灵异事件。R班好热闹。认识了几个郑州那边的大佬知识点Day1讲了几个基础数据结构(树状数,线段树),作业里面的题目很多之前都做过,就当复习了。......