csp-s模拟43,44 A,C,F
题面:https://www.cnblogs.com/Juve/articles/11534880.html
A:
T可以写成如下形式:$T=b^k*S+m*a$,
其中$m=\sum\limits_{i=1}^{k}p_i*b^i$
然后k最多64,所以枚举即可
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#define int long long
#define re register
using namespace std;
int s,t,a,b,ans=0x7fffffff,res,tot=0,n=1;
signed main(){
scanf("%lld%lld%lld%lld",&s,&t,&a,&b);
while(t-s*n>=0){
re int p=t-s*n;
if(p%a==0){
p/=a;
res=0;
for(re int i=tot;i>=0;--i){
int q=pow(b,i);
res+=p/q;
p%=q;
}
ans=min(res+tot,ans);
}
n*=b;
++tot;
}
printf("%lld\n",ans);
return 0;
}
C:
有一个贪心策略
对于每一个点,我们找能加热到它的加热器中右端点最大的一个,然后加热
如果没有符合的就用特殊加热器
如果扫到当前点它已经加热超过p了就跳过
然后有一个部分分算法
如果p很小,我们可以枚举特殊加热器的使用次数,提前给他们加热,然后用贪心策略解决
之后我们优化贪心
我们发现预先枚举的使用特殊加热器的次数所得到的答案具有单谷性质,所以我们可以三分
修改操作用差分和树状数组即可
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<queue>
#define int long long
#define re register
using namespace std;
const int MAXN=1e5+5;
int n,m,t,p[MAXN],maxx=0,ans,g[MAXN],c[MAXN],l,r;
struct node{
int l,r;
friend bool operator < (node a,node b){
return a.l==b.l?a.r<b.r:a.l<b.l;
}
}pos[MAXN];
int lowbit(int x){
return x&-x;
}
int update(int x,int val){
while(x<=n){
c[x]+=val;
x+=lowbit(x);
}
}
int query(int x){
int res=0;
while(x>0){
res+=c[x];
x-=lowbit(x);
}
return res;
}
int check(int k){
int res=k*t;
for(int i=1;i<=n;++i) c[i]=0;
for(int i=1;i<=n;++i){
int q=query(i);
if(q+k>=p[i]) continue;
if(g[i]==0||g[i]>n){
return -0x7fffffffffffffff;
}else{
int tim=p[i]-q-k;
res+=tim;
update(i,tim);
update(g[i]+1,-tim);
}
}
return -res;
}
signed main(){
scanf("%lld%lld%lld",&n,&m,&t);
for(int i=1;i<=n;++i){
scanf("%lld",&p[i]);
maxx=max(maxx,p[i]);
}
for(int i=1;i<=m;++i)
scanf("%lld%lld",&pos[i].l,&pos[i].r);
sort(pos+1,pos+m+1);
int j=1,mx=0;
for(int i=1;i<=n;++i){
if(mx<i) mx=0;
while(j<=m&&pos[j].l<=i) mx=max(mx,pos[j++].r);
g[i]=mx;
}
l=0,r=maxx;
while(r-l>2){
int lmid=(l+r)>>1;
int rmid=lmid+1;
if(check(lmid)<=check(rmid)) l=lmid;
else r=rmid;
}
ans=min(min(-check(l),-check(r)),-check(l+1));
printf("%lld\n",ans);
return 0;
}
F:
30分dp:设f[i][j]表示前i个操作,指针一个在p[i],一个在j的最小代价
转移:
$f[i][j]=min{f[i-1][j]+abs(pos[i]-pos[i-1])}$
$f[i][pos[i-1]]=min(f[i][pos[i-1]],f[i-1][j]+abs(j-pos[i]))$
然后考虑优化
第一个式子我们可以用线段树的区间加
第二个式子我们把abs拆开,用线段树维护f[i][j]+j和f[i][j]-j的最小值
具体操作:先用线段树分别找f[i][j]+j和f[i][j]-j的最小值,比较f[i][j]+j-pos[i]和f[i][j]-j+pos[i],
然后将整个区间加上abs(pos[i]-pos[i-1]),最后将pos[i-1]处的权值修改为上面的最小值
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define int long long
#define re register
using namespace std;
const int MAXN=1e5+5;
int n,q,a,b,pos[MAXN];
struct node{
int val,min1,min2,l,r,laz;
}tr[MAXN<<2];
void pushup(int k){
tr[k].val=min(tr[k<<1].val,tr[k<<1|1].val);
tr[k].min1=min(tr[k<<1].min1,tr[k<<1|1].min1);
tr[k].min2=min(tr[k<<1].min2,tr[k<<1|1].min2);
}
void down(int k){
tr[k<<1].val+=tr[k].laz;
tr[k<<1].min1+=tr[k].laz;
tr[k<<1].min2+=tr[k].laz;
tr[k<<1].laz+=tr[k].laz;
tr[k<<1|1].val+=tr[k].laz;
tr[k<<1|1].min1+=tr[k].laz;
tr[k<<1|1].min2+=tr[k].laz;
tr[k<<1|1].laz+=tr[k].laz;
tr[k].laz=0;
}
void build(int k,int l,int r){
tr[k].l=l,tr[k].r=r;
tr[k].laz=0;
tr[k].val=tr[k].min1=tr[k].min2=0x7fffffff;
if(l==r){
tr[k].val=tr[k].min1=tr[k].min2=0x7fffffff;
if(l==a){
tr[k].val=abs(pos[1]-b);
tr[k].min1=tr[k].val-l;
tr[k].min2=tr[k].val+l;
}
if(l==b){
tr[k].val=abs(pos[1]-a);
tr[k].min1=tr[k].val-l;
tr[k].min2=tr[k].val+l;
}
return ;
}
int mid=(l+r)>>1;
build(k<<1,l,mid),build(k<<1|1,mid+1,r);
pushup(k);
}
void update(int k,int opt,int val){
int l=tr[k].l,r=tr[k].r;
if(l==r){
tr[k].val=val;
tr[k].min1=tr[k].val-tr[k].l;
tr[k].min2=tr[k].val+tr[k].l;
return ;
}
if(tr[k].laz) down(k);
int mid=(l+r)>>1;
if(opt<=mid) update(k<<1,opt,val);
else update(k<<1|1,opt,val);
pushup(k);
}
void change(int k,int opl,int opr,int val){
int l=tr[k].l,r=tr[k].r;
if(opl<=l&&r<=opr){
tr[k].val+=val;
tr[k].min1+=val;
tr[k].min2+=val;
tr[k].laz+=val;
return ;
}
if(tr[k].laz) down(k);
int mid=(l+r)>>1;
if(opl<=mid) change(k<<1,opl,opr,val);
if(opr>mid) change(k<<1|1,opl,opr,val);
pushup(k);
}
int query1(int k,int opl,int opr){
int l=tr[k].l,r=tr[k].r;
if(opl<=l&&r<=opr){
return tr[k].min1;
}
if(tr[k].laz) down(k);
int mid=(l+r)>>1,res=0x7fffffff;
if(opl<=mid) res=min(res,query1(k<<1,opl,opr));
if(opr>mid) res=min(res,query1(k<<1|1,opl,opr));
return res;
}
int query2(int k,int opl,int opr){
int l=tr[k].l,r=tr[k].r;
if(opl<=l&&r<=opr){
return tr[k].min2;
}
if(tr[k].laz) down(k);
int mid=(l+r)>>1,res=0x7fffffff;
if(opl<=mid) res=min(res,query2(k<<1,opl,opr));
if(opr>mid) res=min(res,query2(k<<1|1,opl,opr));
return res;
}
signed main(){
scanf("%lld%lld%lld%lld",&n,&q,&a,&b);
for(re int i=1;i<=q;++i) scanf("%lld",&pos[i]);
build(1,1,n);
for(int i=2;i<=q;++i){
int res=min(query1(1,1,pos[i])+pos[i],query2(1,pos[i],n)-pos[i]);
change(1,1,n,abs(pos[i]-pos[i-1]));
update(1,pos[i-1],res);
}
printf("%lld\n",tr[1].val);
return 0;
}
csp-s模拟43,44 A,C,F的更多相关文章
- csp-s模拟测试44「D·E·F」
用心出题,用脚造数据 乱搞场 1 #include<bits/stdc++.h> 2 #define re register 3 #define int long long 4 #defi ...
- Noip模拟43 2021.8.18
T1 地一体 可以树形$dp$,但考场没写出来,只打了没正确性的贪心水了$30$ 然后讲题的时候B哥讲了如何正确的贪心,喜出望外的学习了一下 不难发现 每次士兵都会直接冲到叶子节点 从深的点再返回到另 ...
- 8.18考试总结[NOIP模拟43]
又挂了$80$ 好气哦,但要保持优雅.(草 T1 地衣体 小小的贪心:每次肯定从深度较小的点向深度较大的点转移更优. 模拟一下,把边按链接点的子树最大深度排序,发现实际上只有上一个遍历到的点是对当前考 ...
- [考试反思]0916csp-s模拟测试44:可笑
出现了有史以来第一个3首杀AK啊...然而跟我没有丝毫关系 (曾经还是有一次考试差点就有那么一点关系的...) 然而反正我考得很水就是了.不是很垃圾,而是很水. 这套题是真的水... T1不会证复杂度 ...
- 2019.9.16 csp-s模拟测试44 反思总结
虽然说好像没有什么写这个的价值OAO 来了来了来写总结了,不能怨任何东西,就是自己垃圾x 开题顺序又和主流背道而驰,先一头扎进了公认最迷的T2,瞎搞两个小时头铁出来,然后T1和T3爆炸.基础很差,全靠 ...
- noip模拟43
A. 第一题 儿子遍历顺序按深度由小到大即可 B. 第二题 二分最小值,以点权作为初始距离跑最长路即可 直接用大根堆跑 \(dij\) 会 \(T\),考虑初始权值可以处理,且边权一定,用类似蚯蚓的方 ...
- NOIP模拟22「d·e·f」
T1:d 枚举. 现在都不敢随便打枚举了. 实际上我们只关注最后留下的矩阵中最小的长与宽即可. 所以我们将所有矩阵按a的降序排列. 从第\(n-m\)个开始枚举. 因为你最多拿 ...
- [考试总结]noip模拟43
这个题目出的还是很偷懒.... 第一题...第二题...第三题...四.... 好吧... 这几次考得都有些问题,似乎可能是有些疲惫,脑袋也是转不太动,考完总觉得自己是能力的问题,但是改一分钟之后会发 ...
- 模拟浏览器搜索功能(Ctrl + F)
写的匆忙,示意一下,有待完善.把以下代码复制到文本文件中,把文件扩展名改为.html就可以运行了. <html> <head> <style type="tex ...
随机推荐
- eclipse查看源码的配置
1.打开eclipse软件,点击window-preference 2.在弹出框中选择java-Installed JRES,选中的默认就行,然后点一下选中的,点击edit 3.弹出框中选择第二个,展 ...
- Vue+Iview+Node 登录demo
1.相关组件安装 axios iview js-cookie crypto-js 2.子父组件传值.监听窗体大小改变.记住密码 .自定义组件(事件 .props) created:实例已经创建完 ...
- LUOGU P2290 [HNOI2004]树的计数(组合数,prufer序)
传送门 解题思路 \(prufer\)序,就是所有的不同的无根树,都可以转化为唯一的序列.做法就是每次从度数为\(1\)的点中选出一个字典序最小的,把这个点删掉,并把这个点相连的节点加入序列,直到只剩 ...
- 小程序修改默认的radio样式
1.wxml: <radio-group class="radio-group" bindchange="radioChange"> <vie ...
- 缓冲(cache)和缓存(buffer)
缓存: 指把常用数据存储到可以快速获取的区域,以备重复利用 一般叫做cache. 缓存能提高效率 缓冲: 是指在数据流转过程中,不同层次速度不一致时,利用缓冲区来缓解上下层之间速率问题(性能差异) 一 ...
- MongoDB后台运行
文章目录 命令方式(推荐) 命令行和配置文件方式 命令行: 配置文件: 命令方式(推荐) 如果想在后台运行,启动时只需添加 --fork函数即可. fork: 以守护进程的方式运行MongoDB. 指 ...
- UVA 511 Do You Know the Way to San Jose?
题目链接:https://vjudge.net/problem/UVA-511 题目翻译摘自<算法禁赛入门经典> 题目大意 有 n 张地图(已知名称和某两个对角线端点的坐标)和 m 个地名 ...
- Day 6:集合(set)
集合(set)定义:由不同元素组成的集合,集合中是一组无序排列的可hash值,可以作为字典的key特性:集合里面数据类型是不可变的1.可变的数据类型:列表,字典2.不可变的数据类型:数字.元组.字符串 ...
- Hive学习笔记简版
一.概述 1. Hive是Apache提供的基于Hadoop的数据仓库管理工具2. Hive提供了类SQL语言来操作Hadoop,底层会将SQL转化为MapReduce来执行,所以效率会比较低3. H ...
- Redis Cluste部署
一.原生搭建篇Cluster了解cluster的架构 Redis-cluster是使用的是一致性哈希算法来切分数据存储,总计16383个槽,分成16383/N(redis节点)个分区,存取时将key转 ...