2021.NOI online提高组总结

本文是对2021年NOI在线提高组竞赛的总结,涉及了愤怒的小N问题,通过深度优先搜索求解二进制中1的奇数个数奖励关卡。积木小赛中,需特别处理全相同字符的情况,采用O(n^3)算法。岛屿探险题目,根据题目描述进行模拟解决。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1.愤怒的小N
自己可以推出奖励关卡在为二进制中有奇数个1的数,就打了一遍dfs,推出奖励关卡的编号,一遍输入k,一边加,注意在dfs时比较当前数与N的大小,由于N过大所以用字符串比较

#include<bits/stdc++.h>
#define LL long long
using namespace std;
const LL mod=1e9+7;
int a[586],k,m=0;
LL b[550],c[550],len,ans=0;
string n;
bool f[mod-10];
LL qiuzhi(int ws)
{
	LL sum=0;
	for(int i=0;i<=ws;i++)
	{
		if(a[i]==1) sum+=(1<<i);
	}
	return sum%mod;
}
bool pd()
{
	for(int i=len-1;i>=0;i++)
	{
		if(a[i]==1&&n[i]=='0') return 1;
		if(a[i]==0&&n[i]=='1') return 0;
	}
	return 0;
}
void dfs(int sum,int ws)
{
	if(ws>len||pd()==1) return;
	
	a[ws]=1;
	dfs(sum+1,ws+1);
	a[ws]=0;
	dfs(sum,ws+1);
	if(sum%2==1)
	{
		int jia=qiuzhi(ws);
		if(f[jia]==0)
		{
			f[jia]=1;
			c[++m]=jia;
		}
		return;
	}
}
LL poww(LL a,LL b)
{
	a%=mod;
    LL ans=1;
    while(b)
    {
          ans*=a;
          b--;
    }
    return ans%mod;
}
int main()
{
	freopen("angry.in","r",stdin);
	freopen("angry.out","w",stdout);
	cin>>n; 
	len=n.size();
	cin>>k;
	dfs(0,0);
	for(int i=0;i<k;i++)
	{
		LL kk;
		cin>>kk;
		for(int j=1;j<=m;j++)
		{
			ans+=kk*(poww(c[j],i))%mod;
			ans%=mod;
		}
	}
	cout<<ans%mod<<endl;
	return 0;
				 

}

积木小赛
注意第一组数据中的全部字母相等,特判一下,即可拿到10分,其他的O(n3)O(n^3)O(n3)枚举0,洛谷拿了70。

#include<bits/stdc++.h>
using namespace std;
int n,sum=0;
string a,b;
set <string> s1;
int main()
{
	freopen("block.in","r",stdin);
	freopen("block.out","w",stdout);
	cin>>n;
	cin>>a>>b;
	bool f=0;
	for(int i=1;i<a.size();i++) 
	{
		if(a[i]!=a[i-1])
		{
			f=1;
			break;
		}
	}
	if(f==0)
	{
		cout<<a.size();
		return 0;
	}
	for(int i=0;i<n;i++)
	{
		for(int j=1;i+j<=n;j++)
		{
			int bh=i;
			int k=0;
			string s2;
			for(int k=i;k<i+j;k++)
			{
				s2+=b[k];
			}
			for(;k<n;k++)
			{
				if(a[k]==b[bh])
				{
					bh++;
					if(bh==i+j)
					{
						s1.insert(s2);
						break;
					}
				}
			}
				
		}
	}
	cout<<s1.size();
    return 0;
}

岛屿探险
依照题目大意进行模拟,洛谷20.

#include<bits/stdc++.h>
#define LL long long
using namespace std;
const int MAXN=1e5+7;
int n,q;
struct island{
	int h,t;
}a[MAXN];
int main()
{
	freopen("island.in","r",stdin);
	freopen("island.out","w",stdout);
	scanf("%d%d",&n,&q);
	for(int i=1;i<=n;i++)
	{
		scanf("%d%d",&a[i].t,&a[i].h );
	}
	while(q--)
	{
		int l,r,sh,st,ans=0;
		scanf("%d%d%d%d",&l,&r,&st,&sh);
		for(int i=l;i<=r;i++)
		{
			if((a[i].t^st)<=min(a[i].h,sh)) ans++;
		}
		printf("%d\n",ans);
	}
	return 0;
} 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值