加载中…

返回上一页

CSP-S模拟17

下发文件

虽然英文题面网上都有,但是除 T3 外请不要转载这些题目的题面. 毕竟翻译是有知识产权的

A. 最大匹配

题面
内存限制:512 MiB 时间限制:1000 ms 标准输入输出
题目类型:传统 评测方式:文本比较

题目描述

给出 个数对 ,你需要把它们配成 对,一对的贡献定义为 。请找到最大的贡献总和。

输入格式

第一行一个正整数 ,接下来 行每行一个数对。

输出格式

输出最大的贡献之和。

样例

样例输入

2
0 10
7 7
9 4
2 15

样例输出

18

数据范围与提示

对于 的数据,
对于 的数据,

,那么 ij 组合可以产生的最大贡献为 .

那么我们只需要保证 | ci - cj | 尽可能大.

所以这道题就转化成了找到 ci 最大的与 ci 最小的并将它们配对. 那么就只需要按照 ci 排序,最后前一半减小的那个值、后一半加大的那个值即可.

点击查看代码
#include<bits/stdc++.h>
#define ll long long
#define ld long double
#define rg register
#define rll rg ll
#define maxn 200001
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
inline ll read()
{
	rll f=0,x=0;rg char ch=getchar();while(ch<'0'||ch>'9') f|=ch=='-',ch=getchar();
	while(ch>='0'&&ch<='9') x=(x<<3)+(x<<1)+(ch^'0'),ch=getchar();return f?-x:x;
}
inline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
struct node
{
	ld c; ll id;
	inline friend bool operator<(rg node a,rg node b) { return a.c<b.c; }
}c[maxn];
ll n,ans,ansk;
ll a[maxn],b[maxn];
int main()
{
	n=read();for(rll i=1;i<=n<<1;i++) a[i]=read(),b[i]=read(),c[i]=(node){((ld)a[i]+b[i])/2,i};
	sort(c+1,c+(n<<1)+1);
	for(rll i=n+1;i<=n<<1;i++) ans+=max(a[c[i].id],b[c[i].id]);
	for(rll i=1;i<=n;i++) ans-=min(a[c[i].id],b[c[i].id]);
	write(ans);
	return 0;
}

B. 挑战ABC

题面
内存限制:512 MiB 时间限制:1000 ms 标准输入输出
题目类型:传统 评测方式:Special Judge

题目描述

有一个只包括A,B,C三种字符的字符串。你可以进行任意次操作:把一段连续区间改成一种字符。请用最少的操作次数,使得字符串中A,B,C出现的次数相等。

输入格式

第一行一个正整数 ,接下来一个长为 的字符串。

输出格式

第一行输出操作数,接下来每行输出一个操作,格式为l r c。如果有多种方案,输出任意一种。

样例

样例输入1

1
AAA

样例输出1

2
2 2 B
3 3 C

样例输入2

3
ABABCABAB

样例输出2

1
1 2 C

数据范围与提示

对于 的数据,
对于 的数据,

很显然,答案一定不会多于 2.

为什么?因为显然 因为最优方案一定是把整个连续的区间全部改成一个字母.

那么分别考虑 012 的情况.

  1. 0

    判断一下如果不需要操作直接输出. 虽然数据里没有 0 的点

if(cnt[1][(n<<1)+n]==cnt[2][(n<<1)+n]&&cnt[2][(n<<1)+n]==cnt[3][(n<<1)+n]) { putchar('0');putn; return 0; }
  1. 1

    用一个双指针,枚举左端点 l,然后找到第一个位置 r 使得区间 [l,r] 至少已有多余数量的 BC(假设当前枚举的是 A). 如果这个位置正好满足相等,直接覆盖即可.

inline void chk(rll x)
{
	rll y=x%3+1,z=(x+1)%3+1;
	for(rll l=1,r=1;l<=(n<<1)+n;l++)
	{
		r=max(l,r); while(r<=(n<<1)+n&&(cnt[y][r]-cnt[y][l-1]<cnt[y][(n<<1)+n]-n||cnt[z][r]-cnt[z][l-1]<cnt[z][(n<<1)+n]-n)) r++;
		if(cnt[y][r]-cnt[y][l-1]==cnt[y][(n<<1)+n]-n&&cnt[z][r]-cnt[z][l-1]==cnt[z][(n<<1)+n]-n) { putchar('1');putn; write(l);put_;write(r);put_;putchar(x|'@'); fl=1; return; }
	}
}

main()
{
	chk(1);if(fl) return 0;chk(2);if(fl) return 0;chk(3);if(fl) return 0;
}
  1. 2

    找到最小的 r,使得 [1,r] 中出现次数最多的字符出现 n 次. 仍然假设当前枚举的是 A,那么剩余需要的 B 的数量就是 n - cntB [1 ~ r]. 所以把这一段区间的变为 B,后面的变为 C.

inline void chk2(rll x)
{
	rll y=x%3+1,z=(x+1)%3+1;putchar('2');putn;
	write(pos+1);put_;write(pos+n-cnt[y][pos]);put_;putchar(y|'@');putn;
	write(pos+n-cnt[y][pos]+1);put_;write((n<<1)+n);put_;putchar(z|'@');putn;
}

main()
{
	chk2(s[pos]^'@');
}

异或 “@” 是卡常的,其实就是 1A2B3C.

C. 三级跳

题面(LOJ 3153
内存限制:512 MiB 时间限制:4000 ms 标准输入输出
题目类型:传统 评测方式:文本比较

题目描述

有一条很长的路,被划分为 段并从 编号。每一段都一个坚固程度,第 段路的坚固程度为

JOI 君是一位有天赋的体育明星。他将在这条路上进行三级跳。一次三级跳包含三次连续的跳跃动作。设 为 JOI 君进行三级跳时三个起跳点的所在段,那么需要满足以下条件:

  • 。即:起跳点所在段需要严格递增;
  • 。即:第一次的跳跃距离应该不大于第二次的跳跃距离。

JOI 君将进行 次三级跳。第 次三级跳的所有起跳点所在段编号都在 范围内。换句话说,必须保证

JOI 君想在更坚固的段上起跳。对于每次三级跳,JOI 君想知道起跳点的最大坚固程度之和。

写一个程序,在给定路的段数和每次三级跳的信息的情况下,计算对于每次三级跳,起跳点的最大坚固程度之和。

输入格式

第一行一个整数 ,表示路的段数;

第二行 个整数 ,第 个数表示第 段路的坚固程度;

第三行一个整数 ,表示 JOI 君进行了 次三级跳;

接下来 行,每行两个整数 ,表示每次三段跳进行的区间。

输出格式

输出 行,第 行表示对第 个询问做出的回答。

样例

样例输入1

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

样例输出1

12
9
12

对于第一次三级跳,JOI 君在 段起跳,最大坚固程度之和为

对于第二次三级跳,JOI 君在 段起跳,最大坚固程度之和为 ,如果他在 段起跳,得到的坚固程度之和为 ,但这不满足 ,因此舍去;

对于第三次三级跳,JOI 君在 段起跳,最大坚固程度之和为 ,如果他在 段起跳,得到的坚固程度之和为 ,但这不满足 ,因此舍去。

样例输入2

5
5 4 4 5 4
1
1 5

样例输出2

14

这组数据满足子任务 的限制条件。

样例输入3

15
12 96 100 61 54 66 37 34 58 21 21 1 13 50 81
12
1 15
3 12
11 14
1 13
5 9
4 6
6 14
2 5
4 15
1 7
1 10
8 13

样例输出3

277
227
72
262
178
181
174
257
208
262
262
113

数据范围与提示

对于所有数据,

详细子任务附加限制及分值如下表:

子任务编号 附加限制 分值
无附加限制

如果存在 p 满足 i<p<ja[p]>max(a[i],a[j]),那么最优的方案一定是选择 ip.

用一个单调栈找出这些 p.

询问时按照 l 从大到小排序,需要插入有用的数对,那么设 n 个标记,每一次对区间内标记取 max 或者查询 a[i] 与标记之和的最大值. 用一个线段树维护最大值即可.

点击查看代码
#include<bits/stdc++.h>
#define ll int
#define rg register
#define rll rg ll
#define maxn 500001
#define pll pair<ll,ll>
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
inline ll read()
{
	rll f=0,x=0;rg char ch=getchar();while(ch<'0'||ch>'9') f|=ch=='-',ch=getchar();
	while(ch>='0'&&ch<='9') x=(x<<3)+(x<<1)+(ch^'0'),ch=getchar();return f?-x:x;
}
inline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
struct node { ll v,mx,tag; }t[maxn<<2];
ll n,m,a[maxn],ans[maxn];
stack<ll> s;
vector<ll> g[maxn];vector<pll> q[maxn];
#define ls(x) (x<<1)
#define rs(x) (x<<1|1)
#define pushup(rt) t[rt].v=max(t[ls(rt)].v,t[rs(rt)].v),t[rt].mx=max(t[ls(rt)].mx,t[rs(rt)].mx)
inline void pushdown(rll rt)
{
	if(t[rt].tag)
		t[ls(rt)].tag=max(t[ls(rt)].tag,t[rt].tag),t[ls(rt)].mx=max(t[ls(rt)].mx,t[ls(rt)].v+t[rt].tag),
		t[rs(rt)].tag=max(t[rs(rt)].tag,t[rt].tag),t[rs(rt)].mx=max(t[rs(rt)].mx,t[rs(rt)].v+t[rt].tag),
		t[rt].tag=0;
}
inline void build(rll rt,rll l,rll r)
{
	if(l==r) { t[rt].v=a[l]; return; } rll mid=(l+r)>>1;
	build(ls(rt),l,mid);build(rs(rt),mid+1,r);pushup(rt);
}
inline void upd(rll rt,rll l,rll r,rll x,rll y,rll v)
{
	if(x>r||y<l) return;
	if(x<=l&&r<=y) { t[rt].tag=max(t[rt].tag,v); t[rt].mx=max(t[rt].mx,t[rt].v+v); return; } pushdown(rt);rll mid=(l+r)>>1;
	if(x<=mid) upd(ls(rt),l,mid,x,y,v); if(y>mid) upd(rs(rt),mid+1,r,x,y,v); pushup(rt);
}
inline ll query(rll rt,rll l,rll r,rll x,rll y)
{
	if(x>r||y<l) return 0;
	if(x<=l&&r<=y) return t[rt].mx; /*cout<<rt<<endl;*/ pushdown(rt);rll mid=(l+r)>>1,ans=0;
	if(x<=mid) ans=query(ls(rt),l,mid,x,y); if(y>mid) ans=max(ans,query(rs(rt),mid+1,r,x,y)); return ans;
}
int main()
{
	n=read();for(rll i=1;i<=n;i++) a[i]=read();m=read();for(rll i=1,l,r;i<=m;i++) l=read(),q[l].push_back((pll) { r=read(),i });
	build(1,1,n); for(rll i=1;i<=n;i++) { while((!s.empty())&&a[s.top()]<a[i]) g[s.top()].push_back(i),s.pop(); if(!s.empty()) g[s.top()].push_back(i); s.push(i); }
	for(rll i=n;i;i--)
	{
		for(rll j=0;j<g[i].size();j++) upd(1,1,n,(g[i][j]<<1)-i,n,a[i]+a[g[i][j]]);
		for(rll j=0;j<q[i].size();j++) ans[q[i][j].second]=query(1,1,n,i,q[i][j].first);
	}
	for(rll i=1;i<=m;i++) write(ans[i]),putn;
	return 0;
}

D. 经典线性基

题面
内存限制:512 MiB 时间限制:1000 ms 标准输入输出
题目类型:传统 评测方式:文本比较

题目描述

取出一段区间内的所有质数放进线性基,这个线性基能组成多少数呢?请你解决这个问题。

输入格式

本题有多组数据。第一行输入数据组数,每组数据输入两个整数 表示一组询问。

输出格式

每组数据输出一行答案。

样例

样例输入

3
2 10
999999940 1000000000
2 1000000000000

样例输出

8
1
1099511627776

数据范围与提示

对于 的数据,
对于没有这档的数据,
对于 的数据,
对于 的数据, 数据不超过100组。

贺的.

点击查看代码
#include<bits/stdc++.h>
#define ll long long
#define rg register
#define ld long double
#define rll rg ll
#define maxn 1000001
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
inline ll read()
{
	rll f=0,x=0;rg char ch=getchar();while(ch<'0'||ch>'9') f|=ch=='-',ch=getchar();
	while(ch>='0'&&ch<='9') x=(x<<3)+(x<<1)+(ch^'0'),ch=getchar();return f?-x:x;
}
inline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
ll t,l,r,lg;
bool notp[maxn],ntp[maxn];
// lbase
ll s[65],num;
inline void ins(rll x)
{
	for(rll i=lg;i+1;i--) if(x&(1ll<<i)) { if(s[i]) x^=s[i]; else { s[i]=x; num++; break; } }
}
inline void shai()
{
	notp[1]=1;
	for(rll i=2;i<maxn;i++) { if(notp[i]) continue; for(rll j=2;i*j<maxn;j++) notp[i*j]=1; }
}
inline void shai(rll l,rll r)
{
	memset(ntp,0,sizeof(ntp)); rll t=ceil(sqrt(r));
	for(rll i=1,tl,tr;i<maxn;i++) if(!notp[i])
	{
		if(i>t) break;tl=ceil((ld)l/i),tr=r/i;for(rll j=max(tl,(ll)2);j<=tr;j++) ntp[i*j-l]=1;
	}
	for(rll i=0;i<=r-l;i++) if(!ntp[i]) ins(l+i);
}
int main()
{

	shai();t=read();while(t--)
	{
		memset(s,0,sizeof(s));num=0;l=read();lg=log2(r=read()+1)+1;
		for(rll i=0;i<=lg+1;i++) if((l&(1ll<<i))&&l+(1ll<<i)<=r)
		{
			if(i<=16) shai(l,l+(1ll<<i)-1); else for(rll j=1;j<=i;j++) ins(1ll<<j); l+=1ll<<i;
		}
		for(rll i=lg+1;i+1;i--) if(l+(1ll<<i)<=r)
		{
			if(i<=16) shai(l,l+(1ll<<i)-1); else for(rll j=1;j<=i;j++) ins(1ll<<j); l+=1ll<<i;
		}
		write(1ll<<num);putn;
	}
	return 0;
}
posted @   1Liu  阅读(66)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 使用C#创建一个MCP客户端
· ollama系列1:轻松3步本地部署deepseek,普通电脑可用
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· 按钮权限的设计及实现

此页面中的资源仅供学习交流使用,请勿转载或外传. 点击“同意”即表示您同意上述内容.

!

Not valid!

点击右上角即可分享
微信分享提示