【比赛】国庆のsurprise
下发文件和题解
前置闲话
今天是国庆节,这个时间吧,我也是见过头一年学校不放假的(可能仅HE). 前年 6 天,去年 3 天,今年 0. 估计明年可能放 -3 天.
但是不过学长给了个惊喜,再次亮相题目. 说是最近看我们做的题目有点难,想给我们送点温暖,结果……
az
# | 用 户 名 | Rubyonly is always here | Su_Zipei is always here | Kaiser_Kell is always here | Pl_er is always here | 总分 |
---|---|---|---|---|---|---|
1
|
lxhcr |
75
01:04:38
|
60
03:26:17
|
100
02:27:27
|
5
03:58:02
|
240
03:58:02
|
2
|
ceredora |
10
03:57:53
|
60
03:35:09
|
100
02:46:04
|
0
03:59:38
|
170
03:59:38
|
3
|
Chen_jr |
30
02:09:42
|
50
02:56:49
|
70
03:37:44
|
5
03:57:45
|
155
03:57:45
|
3
|
Muel_imj |
0
03:59:42
|
100
02:20:47
|
55
03:51:28
|
155
03:59:42
|
|
5
|
chino |
5
03:53:42
|
100
02:39:56
|
40
03:47:35
|
145
03:53:42
|
|
5
|
bikuhiku |
95
03:35:30
|
0
03:24:42
|
50
02:38:18
|
0
03:56:55
|
145
03:56:55
|
7
|
Broken_Eclipse |
30
01:06:30
|
80
03:33:21
|
30
03:43:34
|
0
03:51:10
|
140
03:51:10
|
8
|
Eakang |
30
00:47:34
|
80
02:26:10
|
25
02:58:01
|
135
02:58:01
|
|
8
|
caster |
80
02:42:12
|
55
03:54:56
|
135
03:54:56
|
||
8
|
joke3579 |
0
03:57:43
|
60
01:42:21
|
70
02:59:03
|
5
03:40:09
|
135
03:57:43
|
11
|
wenqizhi1125 |
30
03:04:39
|
60
02:12:56
|
35
01:03:32
|
125
03:04:39
|
|
11
|
hxq |
50
01:18:25
|
75
02:39:31
|
0
03:58:09
|
125
03:58:09
|
|
13
|
abhwolxq |
50
01:24:09
|
70
02:21:24
|
120
02:21:24
|
||
13
|
L |
30
02:30:44
|
60
03:36:39
|
30
02:47:39
|
120
03:36:39
|
|
13
|
Houraisan_Kaguya |
5
03:57:18
|
70
02:20:36
|
45
03:49:58
|
0
03:52:11
|
120
03:57:18
|
16
|
HT_walnut |
60
02:35:16
|
50
01:37:25
|
5
03:56:18
|
115
03:56:18
|
|
17
|
wangruixue |
60
02:24:52
|
50
03:43:25
|
110
03:43:25
|
||
18
|
1Liu |
30
00:35:12
|
50
01:28:36
|
25
02:53:29
|
0
03:31:10
|
105
03:31:10
|
18
|
LovelessDress |
30
02:22:58
|
30
03:36:07
|
35
01:37:36
|
10
02:06:22
|
105
03:36:07
|
18
|
smtwy |
30
03:57:56
|
50
03:24:24
|
25
03:23:59
|
105
03:57:56
|
|
18
|
zasdcn |
5
01:39:27
|
80
03:07:14
|
20
03:59:57
|
0
03:26:34
|
105
03:59:57
|
22
|
Jersan |
30
02:55:20
|
0
03:08:09
|
70
03:40:28
|
0
03:46:27
|
100
03:46:27
|
22
|
ice_cup |
100
02:54:51
|
0
01:27:58
|
0
02:13:36
|
0
03:47:07
|
100
03:47:07
|
22
|
lyin |
100
02:08:53
|
0
03:17:00
|
0
03:57:27
|
0
03:59:18
|
100
03:59:18
|
25
|
crs_line |
50
03:18:16
|
45
03:58:29
|
95
03:58:29
|
||
26
|
La_Pluma |
0
02:51:25
|
60
01:52:42
|
30
03:10:45
|
0
03:16:20
|
90
03:16:20
|
26
|
Starlight |
60
03:43:48
|
30
02:41:38
|
90
03:43:48
|
||
26
|
Clover_BY |
5
02:12:27
|
50
01:52:31
|
25
03:53:10
|
10
03:22:18
|
90
03:53:10
|
26
|
sadom |
30
02:48:01
|
30
03:54:59
|
30
03:02:21
|
0
03:56:20
|
90
03:56:20
|
26
|
morgan |
0
03:45:49
|
80
03:38:02
|
10
03:58:56
|
90
03:58:56
|
|
31
|
Headto_CdqandAKNOIP |
30
03:45:00
|
30
02:48:50
|
15
01:10:01
|
0
03:49:39
|
75
03:49:39
|
32
|
351238 |
10
03:56:41
|
30
03:23:57
|
25
03:52:05
|
0
03:51:32
|
65
03:56:41
|
33
|
sandom |
30
03:03:07
|
20
01:12:47
|
10
01:56:11
|
0
03:40:30
|
60
03:40:30
|
33
|
Anakin |
0
03:18:33
|
30
02:37:11
|
25
03:43:28
|
5
01:10:22
|
60
03:43:28
|
35
|
sandome |
5
02:08:31
|
50
01:11:13
|
55
02:08:31
|
||
36
|
saridom |
30
03:00:37
|
0
01:05:35
|
20
03:27:27
|
50
03:27:27
|
|
36
|
kiritokazuto |
30
03:56:33
|
20
01:36:20
|
0
03:58:44
|
50
03:58:44
|
|
38
|
char_phi |
30
02:15:08
|
10
03:33:43
|
40
03:33:43
|
||
39
|
WintersRain |
30
01:46:14
|
5
03:34:46
|
0
03:07:58
|
35
03:34:46
|
|
39
|
gtm1514 |
30
03:50:16
|
5
03:52:44
|
35
03:52:44
|
||
39
|
IAKIOI |
5
03:48:02
|
30
01:31:24
|
0
03:52:32
|
0
03:56:45
|
35
03:56:45
|
39
|
TSTYFST |
0
03:57:41
|
30
02:13:24
|
5
03:09:31
|
0
03:43:51
|
35
03:57:41
|
43
|
2K22 |
0
03:55:05
|
30
03:55:15
|
0
03:55:38
|
30
03:55:38
|
|
44
|
zcyzcy |
0
00:55:03
|
0
03:10:12
|
0
03:37:19
|
5
02:11:30
|
5
03:37:19
|
“这 T3 不是场切的题吗?”
题面放在下发文件和题解里了,请自取(密码请在 blog 内寻找,其实直接在题库里有,也没啥用)
A. Rubyonly is always here
首先,对于无解的判断:容易发现,经过若干次变换,这两个数的总和永远是一定的. 所以显然当 a + b ≠ c + d (mod p) 是肯定是无解的.
设 sum = a + b,由于数对 (a , b) 可以表示为 (a , sum - a),把每一个数都除以一个 sum,数对就可以表示为 (a , 1-a). 这里除的时候乘一个逆元即可(想一想,为什么?).
又可以发现,经过数次变换之后,这个数对一定会变成 (2a , 1 - 2a) 或者 (2a - 1 , 2 - 2a). 那么易知当 a 变为 c 时, b 一定变为 d.
那么就可以只看 a 的改变. 根据上面的那个式子,变换 k 次时最大会变为 2ka,最小会变为 2ka - (2k - 1). 这种变换最多只会进行 logp 次. 因此,枚举每一个 k,判断 c 是否在上述范围内即可.
点击查看代码
#include<bits/stdc++.h>
#define ll long long
#define rg register
#define sinline static inline
#define rll rg ll
#define maxn 100001
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
sinline 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;
}
sinline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
ll p,q,lg,ans,a,b,sum,id,st,ed,c,d;
sinline ll ksm(rll a,rll b) { rll ans=1; a%=p; for(rll i=b;i;i>>=1) { if(i&1)ans=ans*a%p; a=a*a%p; } return ans; }
int main()
{
p=read();lg=ceil(log2(p));q=read();while(q--)
{
a=read();b=read();c=read();d=read();sum=a+b;
if(((ll)(a+b)%(ll)p)^((ll)(c+d)%(ll)p)) { puts("-1"); continue; }
if(a==c&&b==d) { puts("0"); continue; }
a=a*ksm(sum,p-2)%p,c=c*ksm(sum,p-2)%p;
for(rll k=1;k<=lg;k++)
{
st=(a*(1<<k)-((1<<k)-1))%p;if(st<0) st+=p;
ed=st+(1<<k)-1;
if((st<=c&&c<=ed)||(st<=c+p&&c+p<=ed)||k==lg) { write(k);putn; break; }
}
}
return 0;
}
B. Su_Zipei is always here
这题暴力加莫队能拿 80 分.
看到这个子任务:
对于另外 的数据,
首先想到的就是开一个 300 × n 的数组,记录个前缀和,每次暴力跑一遍这 300 个数.
这就启示了正解做法:
又是根号分治!
对于出现的总次数小于 的颜色,其在每段区间里出现的次数也一定小于 次. 那么把整个序列进行分块,整块处理散块暴力,枚举一个数和前面所有相同颜色数的出现次数,记录产生的贡献.
点击查看代码
#include<bits/stdc++.h>
#define ll int
#define rg register
#define sinline static inline
#define rll rg ll
#define maxn 100001
#define mx 35
#define pll pair<ll,ll>
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
sinline 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;
}
sinline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
struct node { ll a,b,id; };
ll n,q,l,r,bell,belr,mxl,mxr,k,op,sq,ans;
ll a[maxn];
ll cnt[mx+1][maxn],sum[mx+1][mx+1][maxn],tot[maxn];
int main()
{
n=read(),q=read(),op=read(); sq=min((ll)sqrt(n),mx); for(rll i=1;i<=n;i++) a[i]=read();
for(rll i=1;i<=sq;i++)
{
l=(i-1)*(n/sq)+1,r=i*(n/sq);if(r>n) r=n;
for(rll j=1;j<=n;j++) cnt[i][j]=cnt[i-1][j]; for(rll j=l;j<=r;j++) cnt[i][a[j]]++;
}
for(rll i=1;i<=sq;i++) for(rll j=1;j<=sq;j++)
{
for(rll k=1;k<=n;k++) sum[i][j][cnt[j][k]-cnt[i-1][k]]++;
for(rll k=1;k<=n;k++) sum[i][j][k]+=sum[i][j][k-1];
}
while(q--)
{
if((l=(read()+ans*op-1)%n+1)>(r=(read()+ans*op-1)%n+1)) swap(l,r); k=(read()+ans*op-1)%n+1;
ans=0;bell=(l+(n/sq)-1)/(n/sq),belr=(r+(n/sq)-1)/(n/sq);
if(belr-bell<=1)
{
for(rll i=l;i<=r;i++) tot[a[i]]++,ans+=tot[a[i]]==k;
write(ans);putn; for(rll i=l;i<=r;i++) tot[a[i]]=0;continue;
}
mxl=bell*(n/sq),mxr=(belr-1)*(n/sq)+1;ans=sum[bell+1][belr-1][n]-sum[bell+1][belr-1][k-1];
for(rll i=l;i<=mxl;i++) { tot[a[i]]++; ans+=tot[a[i]]+cnt[belr-1][a[i]]-cnt[bell][a[i]]==k; }
for(rll i=mxr;i<=r;i++) { tot[a[i]]++; ans+=tot[a[i]]+cnt[belr-1][a[i]]-cnt[bell][a[i]]==k; }
write(ans);putn; for(rll i=l;i<=mxl;i++) tot[a[i]]=0; for(rll i=mxr;i<=r;i++) tot[a[i]]=0;
}
return 0;
}
C. Kaiser_Kell is always here
这题想必已经不用多说,是一道数据结构大水题.
我赛时以为空间不够打了线段树又删了
第二问,见CSP-S模拟7的自然数题目. 线段树更新操作相同,查询改一下即可.
第一问,让求区间 mex 的 mex. 由下面的内容可以知道(我懒得打了):
把每个点的 mex 值记录一下,在更新线段树权值时也记录一下区间 mex. 查询时看第一个没有出现的数即可.
点击查看代码
#include<bits/stdc++.h>
#define ll int
#define rg register
#define sinline static inline
#define rll rg ll
#define maxn 1000001
#define pll pair<ll,ll>
#define put_ putchar(' ')
#define putn putchar('\n')
using namespace std;
sinline 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;
}
sinline void write(rll x) { if(x<0) putchar('-'),x=-x;if(x>9) write(x/10);putchar(x%10|'0'); }
struct node
{
ll l,r,id;
inline friend bool operator<(rg node a,rg node b) { if(a.l==b.l) return a.r<b.r; return a.l<b.l; }
}b[maxn];
struct tree
{
#define ls(x) (x<<1)
#define rs(x) (x<<1|1)
ll v,mn,tag;
}t[maxn<<2];
ll n,q,a[maxn],mex[maxn],nx[maxn],pos[maxn],ans[maxn],num=1,mx=1;
bool fl[maxn],vis[maxn];
// __gnu_pbds::gp_hash_table<ll,ll> mp;
#define pushup(rt) t[rt].v=t[ls(rt)].v+t[rs(rt)].v,t[rt].mn=min(t[ls(rt)].mn,t[rs(rt)].mn)
sinline void pushdown(rll rt,rll l,rll r)
{
if(t[rt].tag)
{
rll mid=(l+r)>>1; t[ls(rt)].v=t[rt].tag*(mid-l+1);t[rs(rt)].v=t[rt].tag*(r-mid);
t[ls(rt)].mn=t[rs(rt)].mn=t[ls(rt)].tag=t[rs(rt)].tag=t[rt].tag; t[rt].tag=0;
}
}
sinline void build(rll rt,rll l,rll r)
{
if(l==r) { t[rt].v=t[rt].mn=mex[l]; return; }
rll mid=(l+r)>>1;build(ls(rt),l,mid);build(rs(rt),mid+1,r);pushup(rt);
}
sinline void upd(rll rt,rll l,rll r,rll x,rll y,rll v)
{
if(x<=l&&r<=y) { t[rt].v=v*(r-l+1); t[rt].mn=t[rt].tag=v; vis[t[rt].tag]=1; return; }
pushdown(rt,l,r); 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);
}
sinline ll queryv(rll rt,rll l,rll r,rll x,rll y)
{
if(x<=l&&r<=y) return t[rt].v; pushdown(rt,l,r); rll mid=(l+r)>>1,ans=0;
if(x<=mid) ans+=queryv(ls(rt),l,mid,x,y); if(y>mid) ans+=queryv(rs(rt),mid+1,r,x,y);
return ans;
}
sinline ll querymn(rll rt,rll l,rll r,rll pos)
{
if(l==r) return t[rt].mn; pushdown(rt,l,r); rll mid=(l+r)>>1;
if(pos<=mid) return querymn(ls(rt),l,mid,pos); else return querymn(rs(rt),mid+1,r,pos);
}
int main()
{
mex[0]=1; n=read(); for(rll i=1;i<=n;i++) a[i]=read(); q=read(); for(rll i=1;i<=q;i++) b[i]=(node){read(),read(),i}; sort(b+1,b+q+1);
for(rll i=1;i<=n;i++) { fl[a[i]]=1; mex[i]=mex[i-1]; if(a[i]==mex[i]) while(fl[mex[i]]) mex[i]++; vis[mex[i]]=1; } memset(fl,0,sizeof(fl));
build(1,1,n);// for(rll i=1;i<=n;i++) write(mex[i]),put_;
for(rll i=1;i<=n;i++) pos[i]=n+1;
for(rll i=n;i;i--) { /*if(!mp[a[i]]) nx[i]=n+1;else*/ nx[i]=pos[a[i]];pos[a[i]]=i; }
// mp.clear();
for(rll i=1,now=1,l,r,k;i<=n;i++)
{
while(b[num].l==i) ans[b[num].id]+=queryv(1,1,n,i,b[num].r)-queryv(1,1,n,i,b[num].r-1),num++;
l=i;r=nx[i]-1;k=-1;
while(l<r)
{
rll mid=(l+r)>>1;
if(querymn(1,1,n,mid+1)>a[i]) k=mid+1,r=mid; else l=mid+1;// write(l);put_;write(r);putn;
}
if(k^-1) upd(1,1,n,k,nx[i]-1,a[i]);
}
while(vis[mx]) mx++;write(mx);putn;
for(rll i=1;i<=q;i++) write(ans[i]),put_;
return 0;
}
D. Pl_er is always here
暂咕……
--END--
我的博客: 𝟷𝙻𝚒𝚞
本文链接: https://www.cnblogs.com/1Liu/p/16747340.html
版权声明: 本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!