csps模拟92数列,数对,最小距离题解
题面:https://www.cnblogs.com/Juve/articles/11767225.html
数列:
简化题意:已知a,b,c,求满足$a*x+b*y=c$的$x+y$最小值
然后ex_gcd硬刚就好了,若c为负,则取abs
如果我们设a<b,最优决策点就是x的最小正整数解和最大负整数解
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define int long long
using namespace std;
const int MAXN=1e5+;
int n,a,b,g,val,x,y,ans=;
int ex_gcd(int a,int b,int &x,int &y){
if(!b){
x=,y=;
return a;
}
int d=ex_gcd(b,a%b,x,y);
int t=x;
x=y,y=t-a/b*x;
return d;
}
signed main(){
scanf("%lld%lld%lld",&n,&a,&b);
if(a>b) swap(a,b);
g=ex_gcd(a,b,x,y);
a/=g,b/=g;
x=(x%b+b)%b;
for(int i=;i<=n;++i){
scanf("%lld",&val);
if(val<) val=-val;
if(val%g){
puts("-1");
return ;
}
val/=g;
int p=(x*val%b+b)%b;
int q=(val-a*p)/b;
ans+=min(abs(p)+abs(q),abs(p-b)+abs(q+a));
}
printf("%lld\n",ans);
return ;
}
数对:
队长快跑加了权值
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define int long long
using namespace std;
const int MAXN=1e5+;
int n,ans=,sta[MAXN<<],top=;
struct node{
int a,b,w;
friend bool operator < (node p,node q){
return p.a+p.b<q.a+q.b;
}
}p[MAXN];
int tr[MAXN<<],laz[MAXN<<];
void down(int k){
tr[k<<]+=laz[k],tr[k<<|]+=laz[k];
laz[k<<]+=laz[k],laz[k<<|]+=laz[k];
laz[k]=;
}
int query(int k,int l,int r,int opl,int opr){
if(opl<=l&&r<=opr) return tr[k];
if(laz[k]) down(k);
int mid=(l+r)>>,res=;
if(opl<=mid) res=max(res,query(k<<,l,mid,opl,opr));
if(opr>mid) res=max(res,query(k<<|,mid+,r,opl,opr));
return res;
}
void update(int k,int l,int r,int opl,int opr,int val){
if(opl<=l&&r<=opr){
tr[k]+=val;
laz[k]+=val;
return ;
}
if(laz[k]) down(k);
int mid=(l+r)>>;
if(opl<=mid) update(k<<,l,mid,opl,opr,val);
if(opr>mid) update(k<<|,mid+,r,opl,opr,val);
tr[k]=max(tr[k<<],tr[k<<|]);
}
void change(int k,int l,int r,int opt,int val){
if(l==r){
tr[k]=max(tr[k],val);
return ;
}
if(laz[k]) down(k);
int mid=(l+r)>>;
if(opt<=mid) change(k<<,l,mid,opt,val);
else change(k<<|,mid+,r,opt,val);
tr[k]=max(tr[k<<],tr[k<<|]);
}
signed main(){
//freopen("pair.in","r",stdin);
scanf("%lld",&n);
for(int i=;i<=n;++i){
scanf("%lld%lld%lld",&p[i].a,&p[i].b,&p[i].w);
sta[++top]=p[i].a,sta[++top]=p[i].b;
}
sort(p+,p+n+);
sort(sta+,sta+top+);
top=unique(sta+,sta+top+)-sta-;
for(int i=;i<=n;++i){
p[i].a=lower_bound(sta+,sta+top+,p[i].a)-sta;
p[i].b=lower_bound(sta+,sta+top+,p[i].b)-sta;
}
for(int i=;i<=n;++i){
if(p[i].a<p[i].b){
update(,,top,p[i].a+,p[i].b,p[i].w);
int t=query(,,top,,p[i].a)+p[i].w;
change(,,top,p[i].a,t);
}else{
int t=query(,,top,,p[i].b)+p[i].w;
change(,,top,p[i].a,t);
}
}
printf("%lld\n",tr[]);
return ;
}
最小距离:
多源点spfa,把所有特殊点作为远点跑spfa,此时的dis数组意义就是这个点到所有特殊点中最小那一个的距离,同时记录这个点是从那一个点转移而来,
跑完后枚举所有边,如果边的两段的点不是由同一个特殊点更新而来,那么用dis[u]+dis[v]+val[u,v]更新两个特殊点
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
#define int long long
using namespace std;
const int MAXN=2e5+5;
int n,m,p,x[MAXN];
int to[MAXN<<1],nxt[MAXN<<1],pre[MAXN],val[MAXN<<1],cnt=0,fr[MAXN<<1];
void add(int u,int v,int w){
++cnt,to[cnt]=v,fr[cnt]=u,nxt[cnt]=pre[u],pre[u]=cnt,val[cnt]=w;
}
int dis[MAXN],fro[MAXN],ans[MAXN];
bool vis[MAXN];
queue<int>q;
void spfa(){
memset(dis,0x3f,sizeof(dis));
memset(vis,0,sizeof(vis));
for(int i=1;i<=p;++i){
dis[x[i]]=0,vis[x[i]]=1;
q.push(x[i]);
fro[x[i]]=x[i];
}
while(!q.empty()){
int x=q.front();
q.pop();
for(int i=pre[x];i;i=nxt[i]){
int y=to[i];
if(dis[y]>dis[x]+val[i]){
dis[y]=dis[x]+val[i];
fro[y]=fro[x];
if(!vis[y]) q.push(y),vis[y]=1;
}
}
vis[x]=0;
}
}
signed main(){
//freopen("distance.in","r",stdin);
scanf("%lld%lld%lld",&n,&m,&p);
for(int i=1;i<=p;++i) scanf("%lld",&x[i]);
for(int i=1,u,v,w;i<=m;++i){
scanf("%lld%lld%lld",&u,&v,&w);
add(u,v,w),add(v,u,w);
}
memset(ans,0x3f,sizeof(ans));
spfa();
for(int i=1;i<=cnt;i+=2){
int u=fr[i],v=to[i];
if(fro[u]!=fro[v]){
ans[fro[u]]=min(ans[fro[u]],dis[u]+dis[v]+val[i]);
ans[fro[v]]=min(ans[fro[v]],dis[u]+dis[v]+val[i]);
}
}
for(int i=1;i<=p;++i) printf("%lld ",ans[x[i]]);
puts("");
return 0;
}
csps模拟92数列,数对,最小距离题解的更多相关文章
- 812考试总结(NOIP模拟37)[数列·数对·最小距离·真相]
前言 考得挺憋屈的... 先是搞了两个半小时的 T1 后来发现假了,又没多想跳了.. 然后一看 T2 这不是队长快跑嘛... 先是根据自己的想法打了一遍(考完之后发现是对的..) 然后回想了一下之前的 ...
- [CSP-S模拟测试]:平方数(数学+哈希)
题目传送门(内部题137) 输入格式 第一行,一个正整数$n$. 第二行$n$个正整数$a_1\sim a_n$. 输出格式 输出一个整数,为满足条件的二元组个数. 样例 样例输入: 51 2 3 4 ...
- [CSP-S模拟测试]:数列(数学)
题目传送门(内部题95) 输入格式 第一行三个整数$n,a,b$,第二行$n$个整数$x_1\sim x_n$表示数列. 输出格式 一行一个整数表示答案.无解输出$-1$. 样例 样例输入:2 2 3 ...
- CSPS模拟 92
为什么每次我的flag都会倒? skyh:12:15之前你把T2改出来我吃屎. ----12:10 于是12:12把线段树打完 12:13把主函数打完,过样例,带着一个sb错误交了,WA飞. 然后我就 ...
- csp-s模拟100,101T1,T2题解
题面:https://www.cnblogs.com/Juve/articles/11799325.html 我太蒻了只会T1T2 组合: 欧拉路板子?不会呀... 然后打了个优化,防止暴栈 #inc ...
- csps模拟84Smooth,Six,Walker题解
题面:https://www.cnblogs.com/Juve/articles/11733280.html smooth: 暴力强筛到7e7有60分... 正解: 维护一个队列,存所有的B-光滑数, ...
- csp-s模拟测试52平均数,序列题解
题面:https://www.cnblogs.com/Juve/articles/11602244.html 平均数: 第k个平均数不好求,我们考虑二分,转化成平均数小于x的有几个 虑把序列中的每个数 ...
- CSP-S模拟41影子,玫瑰花精题解
题面:https://www.cnblogs.com/Juve/articles/11523567.html 影子: 暴力方法:枚举每一对点暴力统计最小权 优化:考虑并查集,枚举每个点,如果没有被访问 ...
- Codeforces VK Cup 2015 - Qualification Round 1 D. Closest Equals 离线线段树 求区间相同数的最小距离
D. Closest Equals Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOnline/prob ...
随机推荐
- C语言static和局部变量
#include <stdio.h> void test(); int main() { /************************************************ ...
- Vue双向数据绑定原理深度解析
首先,什么是双向数据绑定?Vue是三大MVVM框架之一,数据绑定简单来说,就是当数据发生变化时,相应的视图会进行更新,当视图更新时,数据也会跟着变化. 在分析其原理和代码的时候,大家首先了解如下几个j ...
- ttytype - 终端设备映射的默认终端类型
DESCRIPTION(描述) /etc/ttytype 文件把termcap/terminfo中的终端类型名与tty行关联起来.每行包括一种终端类型,后面跟着空格,然后是tty名(不带 /dev/ ...
- 基于LNMP架构部署wordpress
[root@localhost ~]# yum -y install unzip[root@localhost ~]# unzip wordpress-5.2.3.zip[root@localhost ...
- (PASS)字符数组\字符串数组 和 字符串 的相互转换
1,字符数组 转换为 字符串 java可以使用两种方法直接将字符数组转为字符串. 方法1:直接在构造String时转换. char[] data = {'a', 'b', 'c'}; String s ...
- python学习笔记(十)——正则表达式和re模块
#正则表达式和re模块 # match(pattern, string,[flag]) #在字符串开始时进行匹配 # pattern 正则表达式 # string 要匹配的字符串 # [flag] 可 ...
- GC线程是否为守护线程?
GC是垃圾收集的意思,Java提供的GC功能可以自动监测对象是否超过作用域从而达到自动回收内存的目的,从而有效的防止内存泄露.要请求垃圾收集,可以调用下面的方法之一:System.gc()或Runti ...
- FontFamily 和Font 的区别
GDI+ 将字样相同但字形不同的字体分组为字体系列.例如,下面是同一个字样(Arial),不同的字形 : ----------------------------------------------- ...
- 51nod 1556 计算(递推)
传送门 解题思路 在一个网格图上走\(n\)步,每次可以向右上,右下,右,但必须在第一象限,最后从\((0,0)\)走到\((n,0)\)的方案数为默慈金数.递推式为\(m[i+1]=\frac{(2 ...
- OpenStack与KVM的区别与联系
转:https://www.aliyun.com/zixun/content/2_6_280418.html OpenStack与KVM都是目前IT界比较热门的两个词汇.它们都是开源的,都与Linux ...