Educational Codeforces Round 66 (Rated for Div. 2)
A.直接模拟。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
typedef long long ll;
using namespace std; ll n,k,T,ans; int main(){
for (cin>>T; T--; ){
cin>>n>>k; ans=;
for (ll x=n; x; x/=k,ans++) ans+=x%k;
cout<<ans-<<endl;
}
return ;
}
B.直接模拟,用栈记录下每层的循环次数,注意当总次数超过2^31时就直接记成2^31。
#include<cstdio>
#include<algorithm>
#include<iostream>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
typedef long long ll;
using namespace std; const int N=;
int T,top;
ll x,t,s[N]; int main(){
s[++top]=;
for (cin>>T; T--; ){
char op[]; cin>>op;
if (op[]=='f') cin>>t,top++,s[top]=(s[top-]<1ll<<)?t*s[top-]:s[top-];
else if (op[]=='e') top--; else x+=s[top];
if (x>=1ll<<){ cout<<"OVERFLOW!!!"<<endl; return ; }
}
cout<<x<<endl;
return ;
}
C.离一个点最近的k个点一定是一个区间,枚举每个长度为k的区间即可。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
typedef long long ll;
using namespace std; const int N=;
int n,k,T,ans,x,a[N]; int main(){
for (scanf("%d",&T); T--; ){
scanf("%d%d",&n,&k);
rep(i,,n) scanf("%d",&a[i]);
sort(a+,a+n+); ans=a[n]-a[]; x=a[];
rep(i,,n-k) if ((a[i+k]-a[i]+)/<ans) ans=(a[i+k]-a[i]+)/,x=(a[i]+a[i+k]+)/;
printf("%d\n",x);
}
return ;
}
D.每设一个断点相当于将贡献加上之后所有数的和,那么将所有后缀和放在一起排序,取贡献最小的几个断点即可。注意开头是一定要设断点的。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
typedef long long ll;
using namespace std; const int N=;
ll ans,sm[N];
int n,k,s,a[N],id[N],p[N];
bool cmp(int a,int b){ return sm[a]>sm[b]; } int main(){
scanf("%d%d",&n,&k);
rep(i,,n) scanf("%d",&a[i]);
for (int i=n; i; i--) sm[i]=sm[i+]+a[i],id[i]=i;
sort(id+,id+n+,cmp);
rep(i,,k) p[id[i]]=;
rep(i,,n){
if (p[i]) s++;
ans+=1ll*s*a[i];
}
cout<<ans<<endl;
return ;
}
E.倍增记录每个区间往后选2^i个区间最多能延伸到什么位置(保证这2^i个区间首尾不断),预处理的时候先按右端点排序,再用树状数组或者二分找到与当前区间首尾相接的右端点最靠右的区间。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
typedef long long ll;
using namespace std; const int N=;
int n,m,l,r,c[N],nxt[N][];
struct P{ int l,r; }p[N];
bool operator <(const P &a,const P &b){ return a.r>b.r; } int que(int x){ int res=; for (x++; x; x-=x&-x) if (p[c[x]].r>p[res].r) res=c[x]; return res; }
void add(int x,int k){ for (x++; x<=; x+=x&-x) if (p[c[x]].r<=p[k].r) c[x]=k; } int main(){
scanf("%d%d",&n,&m);
rep(i,,n) scanf("%d%d",&p[i].l,&p[i].r);
sort(p+,p+n+);
rep(i,,n) nxt[i][]=que(p[i].r),add(p[i].l,i);
rep(j,,) rep(i,,n) nxt[i][j]=nxt[nxt[i][j-]][j-];
rep(i,,m){
scanf("%d%d",&l,&r); int x=que(l),res=;
if (x==n+){ puts("-1"); continue; }
if (p[x].r>=r){ puts(""); continue; }
for (int i=; ~i; i--) if (nxt[x][i] && p[nxt[x][i]].r<r) res+=<<i,x=nxt[x][i];
res++; x=nxt[x][];
if (p[x].r<r) puts("-1"); else printf("%d\n",res);
}
return ;
}
F.考虑将条件转化:[l,r]值域是[1,r-l+1]等价于[l,r]区间内数两两不同且max(l,r)=r-l+1。首先我们对于每个位置i,可以轻易算出最大的r[i]使得[i,r[i]]中的数两两不同。根据max想到最值分治,然后发现每次遍历区间长度一定不大于min(mid-l,r-mid),于是就在O(nlogn)时间内解决了。
最值分治大概就是,对于当前考虑区间[l,r]找到其中最大/小的数a[mid],然后对[l,mid-1]和[mid+1,r]分别递归下去。合并时,只遍历短的那一边,计算短的那一边的每个数与长的那一边整体产生的贡献。复杂度类比启发式合并可知显然为O(nlogn)。这题中就是每次找到最大值a[mid],然后计算有多少跨过mid的合法区间,根据之前的r[i]数组可以轻松得到答案。
#include<cstdio>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
using namespace std; const int N=;
int n,ans,a[N],b[N],lst[N],lg[N],st[N][]; int Max(int x,int y){ return a[x]>a[y] ? x : y; } int que(int l,int r){ int t=lg[r-l+]; return Max(st[l][t],st[r-(<<t)+][t]); } void work(int l,int r){
int mid=que(l,r);
rep(i,max(l,mid-a[mid]+),min(mid,r-a[mid]+)) if (b[i]>=a[mid]) ans++;
if (l<mid) work(l,mid-);
if (r>mid) work(mid+,r);
} int main(){
scanf("%d",&n);
rep(i,,n) scanf("%d",&a[i]),st[i][]=i;
b[n+]=n+; rep(i,,n) lst[i]=n+;
for (int i=n; i; i--) b[i]=min(b[i+]+,lst[a[i]]-i),lst[a[i]]=i;
rep(i,,n) lg[i]=lg[i>>]+;
rep(j,,lg[n]) rep(i,,n-(<<j)+) st[i][j]=Max(st[i][j-],st[i+(<<(j-))][j-]);
work(,n); printf("%d\n",ans);
return ;
}
G.一个显然的DP是,f[i][j]表示前i个数分j段的最小总和,转移枚举第j段的开头,复杂度O(kn^2)。考虑对每个j做类似CDQ分治,先递归算出[l,mid]和[mid+1,r]两个区间的答案,再计算[mid+1,r]中的每个位置的最后一段开头在[l,mid]中时,能否更新答案。我们从mid开始向前向后分别求后缀和与前缀和,然后分“最后一段的最大值在[l,mid]还是[mid+1,r]”两种情况转移,发现方程是一个关于前缀后缀和的一个一次函数。于是问题变为,分治后在线往直线集中加入一条新直线,并实时查询集合中所有直线某个横坐标上的值的最大值。用单调栈维护一个上凸壳,查询时二分即可。注意一个细节是,当新加入的直线斜率和上一条直线斜率相同时,普通的计算交点方法就错了。于是复杂度为O(nklogn)。
#include<cstdio>
#include<algorithm>
#define rep(i,l,r) for (int i=(l); i<=(r); i++)
using namespace std; const int N=,inf=1e9;
int n,k,top,a[N],f[N],g[N],pre[N],suf[N];
struct L{ int k,b; int F(int x){ return k*x+b; } }q[N]; bool cmp(L a,L b,L c){ return 1ll*(a.k-b.k)*(c.b-a.b)<=1ll*(a.k-c.k)*(b.b-a.b); } void ins(L x){
while (top && x.k>=q[top].k) x.b=min(x.b,q[top].b),top--;
while (top> && cmp(q[top-],q[top],x)) top--;
q[++top]=x;
} int calc(int x){
if (!top) return inf;
int l=,r=top;
while (l<r){
int mid=(l+r)>>;
if (q[mid].F(x)<=q[mid+].F(x)) r=mid; else l=mid+;
}
return q[l].F(x);
} void solve(int l,int r){
if (l==r) return;
int mid=(l+r)>>;
solve(l,mid); solve(mid+,r);
suf[mid+]=; for (int i=mid; i>=l; i--) suf[i]=max(suf[i+],a[i]);
pre[mid]=; rep(i,mid+,r) pre[i]=max(pre[i-],a[i]);
top=;
for (int i=r,j=l; i>mid; i--){
while (j<=mid && suf[j+]>=pre[i]) if (g[j++]<inf) ins((L){suf[j],g[j-]-(j-)*suf[j]});
f[i]=min(f[i],calc(i));
}
top=;
for (int i=mid+,j=mid; i<=r; i++){
while (j>=l && suf[j+]<=pre[i]) if (g[j--]<inf) ins((L){j+,g[j+]});
f[i]=min(f[i],calc(-pre[i])+i*pre[i]);
}
} int main(){
scanf("%d%d",&n,&k);
rep(i,,n) scanf("%d",&a[i]),pre[i]=max(pre[i-],a[i]);
rep(i,,n) f[i]=pre[i]*i;
rep(i,,k){
rep(j,,n) g[j]=f[j],f[j]=inf;
solve(,n);
}
printf("%d\n",f[n]);
return ;
}
Educational Codeforces Round 66 (Rated for Div. 2)的更多相关文章
- Educational Codeforces Round 66 (Rated for Div. 2) B. Catch Overflow!
链接:https://codeforces.com/contest/1175/problem/B 题意: You are given a function ff written in some bas ...
- Educational Codeforces Round 66 (Rated for Div. 2) A. From Hero to Zero
链接:https://codeforces.com/contest/1175/problem/A 题意: You are given an integer nn and an integer kk. ...
- Educational Codeforces Round 66 (Rated for Div. 2) A
A. From Hero to Zero 题目链接:http://codeforces.com/contest/1175/problem/A 题目 ou are given an integer n ...
- Educational Codeforces Round 60 (Rated for Div. 2) - C. Magic Ship
Problem Educational Codeforces Round 60 (Rated for Div. 2) - C. Magic Ship Time Limit: 2000 mSec P ...
- Educational Codeforces Round 60 (Rated for Div. 2) - D. Magic Gems(动态规划+矩阵快速幂)
Problem Educational Codeforces Round 60 (Rated for Div. 2) - D. Magic Gems Time Limit: 3000 mSec P ...
- Educational Codeforces Round 43 (Rated for Div. 2)
Educational Codeforces Round 43 (Rated for Div. 2) https://codeforces.com/contest/976 A #include< ...
- Educational Codeforces Round 35 (Rated for Div. 2)
Educational Codeforces Round 35 (Rated for Div. 2) https://codeforces.com/contest/911 A 模拟 #include& ...
- Codeforces Educational Codeforces Round 44 (Rated for Div. 2) F. Isomorphic Strings
Codeforces Educational Codeforces Round 44 (Rated for Div. 2) F. Isomorphic Strings 题目连接: http://cod ...
- Codeforces Educational Codeforces Round 44 (Rated for Div. 2) E. Pencils and Boxes
Codeforces Educational Codeforces Round 44 (Rated for Div. 2) E. Pencils and Boxes 题目连接: http://code ...
随机推荐
- 02-线性结构3 Reversing Linked List (25 分)
Given a constant K and a singly linked list L, you are supposed to reverse the links of every K elem ...
- 软件工程 “校园汇” 个人IDEA竞选分析与总结
IDEA竞选 19/10/8软件工程课上举行了一次IDEA竞选: 我的竞选IDEA是"校友汇",大学生的在线活动中心. 投票结果: 可以看到,校友会(汇)IDEA竞选结果十分惨淡, ...
- 解决WordPress访问中文标签出现404的几个方法
最近很多主题用户提到安装完WordPress后中文标签出现404的情况,出现这种情况一般修改固定链接设置是没有效果的,多数是windows主机带来的麻烦.网上多数人说要修改核心文件class-wp.p ...
- ThreadLocal是什么
早在JDK 1.2的版本中就提供Java.lang.ThreadLocal,ThreadLocal为解决多线程程序的并发问题提供了一种新的思路.使用这个工具类可以很简洁地编写出优美的多线程程序. 当使 ...
- mysql 面试题 查询出表中某字段的重复值
users 表中有 两个字段 id 和 name 表数据大概如下: id name 1 AAA 2 BBB 3 CCC 4 AAA 请写查 ...
- 经典批处理实现自动关机(BAT)
经典批处理实现自动关机1.BAT @ECHO offTITLE 自动关机程序 作者:廖晓青 :startCLSCOLOR 1frem 使用COLOR命令对控制台输出颜色进行更改MODE con: CO ...
- 秒杀功能压测 jmeter--------重要!!!
线程组里面有三个接口请求,依次为:显示商品列表.登录秒杀平台账户.进行秒杀 对线程组用5000个线程循环10次 设置一下默认配置,之后就不用反复填写了 设置配置文件这个具体功能就是读text文件并且设 ...
- mysqldump: Got error: 1449: The user specified as a definer ('xxx'@'%') does not exist when using LOCK TABLES
开发同学说在测试环境使用mysqldump导出数据的时候遇到以下错误: # mysqldump -uroot -p --all-databases --routines --events --trig ...
- oracle的insert的时候&符号如何插入
chr(38)替换& insert into table values( 'http://localhost:8080/index.action?username=138& ...
- matlab学习笔记11_1低维数组操作
一起来学matlab-matlab学习笔记11 11_1 低维数组操作repmat函数,cat函数,diag函数 觉得有用的话,欢迎一起讨论相互学习~Follow Me 参考书籍 <matlab ...