Mathmen、Codeforces Round #750 (Div. 2)

news/2025/2/10 22:51:34/

昨天的一道题,Mathmen。

Mathmen(贪心,二分)

题意:

给定n个位置,和m个船只,要从一个位置到后面一个位置挨个走
每只船只都有两种属性:行驶距离和花费。
每个位置都有m条船,从一个位置到下一位置选择一艘船,行驶距离至少为两位置间距离。问,如果选择,使得总花费最少?

思路:

思路1:二分
一开始想的是这样二分:将船只按行驶距离和花费排序,找到第一个行驶距离大于间距的船只,答案+=此船花费。 但是可能后面行驶距离更长的船只花费还更少呢?
所以,从第一个行驶距离不小于间距的那条船开始,到后面的所有船都是满足要求的,最小花费为这些船中,花费的最小值。
所以,预先维护每个位置到最后一个位置中,花费的最小值f[i]。
二分加上第一个满足的位置的 f[i] 值就行了。

Code:

const int N = 200010, mod = 1e9+7;
int T, n, m, a[N],b[N], f[N];
PII c[N];int main(){Ios;cin>>T;while(T--){cin>>n>>m;for(int i=1;i<=n;i++) cin>>a[i];sort(a+1,a+n+1);for(int i=2;i<=n;i++) b[i-1]=a[i]-a[i-1];n--;sort(b+1,b+n+1);for(int i=1;i<=m;i++) cin>>c[i].fi>>c[i].second;sort(c+1,c+m+1);f[m+1]=2e9;for(int i=m;i>=1;i--) f[i]=min(f[i+1],c[i].second);int flag=0;ll ans=0;for(int i=1;i<=n;i++){int l=1,r=m;while(l<r){int mid=l+r>>1;if(c[mid].first>=b[i]) r=mid;else l=mid+1;}if(c[l].first>=b[i]) ans+=f[l];else {flag=1;break;}}if(!flag) cout<<ans<<"\n";else cout<<"Impossible\n";}return 0;
}

思路2:贪心
如果正着来的话,每次都要把后面所有满足的都存起来。
正着不行倒着来。

将两个数组都从大到小排序。
设置一个指针,将满足比当前位置大的船的价值都存到优先队列中。
每次取队首元素就行了。

Code:

const int N = 200010, mod = 1e9+7;
int T, n, m, a[N],b[N], f[N];
PII c[N];int main(){Ios;cin>>T;while(T--){cin>>n>>m;for(int i=1;i<=n;i++) cin>>a[i];sort(a+1,a+n+1);for(int i=2;i<=n;i++) b[i-1]=a[i]-a[i-1];n--;sort(b+1,b+n+1,greater<int>());for(int i=1;i<=m;i++) cin>>c[i].fi>>c[i].second;sort(c+1,c+m+1,greater<PII>());priority_queue<int,vector<int>,greater<int> > que;int flag=0;ll ans=0;int idx=1;for(int i=1;i<=n;i++){while(idx<=m&&c[idx].first>=b[i]) que.push(c[idx].second),idx++;if(!que.size()){flag=1;break;}else ans+=que.top();}if(!flag) cout<<ans<<"\n";else cout<<"Impossible\n";}return 0;
}


Codeforces Round #750 (Div. 2)


A.Luntik and Concerts(思维)

思路:

一共a*1+b*2+c*3个,分成两份。判断其模2结果。

Code:

const int N = 200010, mod = 1e9+7;
int T, n, m;int main(){cin>>T;while(T--){int a,b,c;cin>>a>>b>>c;ll x=a+b*2+c*3;if(x%2==0) cout<<0<<endl;else cout<<1<<endl;} return 0;
}

B.Luntik and Subsequences(组合)

题意:

一个长度为 n 的数列,元素总和为 sum。
问这个数列中有多少子序列,其元素总和为sum-1?(子序列(集合)可以为空)

思路:

子序列总和为数列全部元素总和 -1,那么说明只有一个 元素1 没在子序列中。
但是,如果有元素0的话,可以选也可以不选。

设元素1出现了x次,元素0出现了y次。
那么,留下的那个元素1有x种策略。选择的0有2^y种策略。
所以,满足的序列个数为: x ∗ 2 y x*2^{y} x2y

需要注意的是, 2 y 2^y 2y不要用左移运算!!
左移运算需要满足在 int 范围内,超过范围就会溢出为0了。。
所以左移运算只能在 y<31 的情况下使用。

两个月之后更~
左移运算超过int范围也是可以的,只不过要把前面的数字类型换成long long,得出的答案也是 long long 了。
像这样:cout << (1ll << 42);

Code:

const int N = 200010, mod = 1e9+7;
int T, n, m, a[N];int main(){cin>>T;while(T--){cin>>n;int cnt1=0,cnt2=0;ll sum=0;for(int i=1;i<=n;i++){int x;cin>>x;if(x==0) cnt1++;if(x==1) cnt2++;sum+=x;}cout<<(ll)(cnt2*(ll)pow(2,cnt1))<<endl;}return 0;
}

C. Grandma Capa Knits a Scarf(模拟)

题意:

对于一个字符串,问最少执行下面操作多少次,能够将该字符串变成回文串?如果不可,输出-1。
操作:选择一种字符,删除若干个。

思路:

从两端往中间走,找到第一对不同的两个字符。
那么,这两种字符肯定要删除一个。
所以,两种情况讨论,取最优答案。

Code:

const int N = 200010, mod = 1e9+7;
int T, n, m;
char a[N];int main(){Ios;cin>>T;while(T--){cin>>n;for(int i=1;i<=n;i++) cin>>a[i];int l=1,r=n;int tl,tr,ff=0;for(int i=1;i<=n/2;i++){if(a[l]!=a[r]){tl=l,tr=r;ff=1;break;}l++,r--;}if(!ff){cout<<0<<endl;continue;}char c=a[tl],d=a[tr];int lll=tl,rr=tr;int flag=0;int cnt=0;while(tl<tr){if(a[tl]!=a[tr]){if(a[tl]==c) tl++,cnt++;else if(a[tr]==c) tr--,cnt++;else{flag=1;break;}}if(a[tl]==a[tr]) tl++,tr--;}int ans=1e9;if(!flag) ans=min(ans,cnt);cnt=0;flag=0;tl=lll,tr=rr;while(tl<tr){if(a[tl]!=a[tr]){if(a[tl]==d) tl++,cnt++;else if(a[tr]==d) tr--,cnt++;else{flag=1;break;}}if(a[tl]==a[tr]) tl++,tr--;}if(!flag) ans=min(ans,cnt);if(ans!=1e9) cout<<ans<<endl;else cout<<-1<<endl;}return 0;
}

D. Vupsen, Pupsen and 0(构造,思维)

题意:

给定长度为 n 的数组 a。 ( 1 0 4 ≤ a i ≤ 1 0 4 , a i ≠ 0 ) (10^4 ≤ai ≤10^4, ai ≠0) (104ai104,ai=0)
问,能否构造一个数组 b,使得 ai*bi 总和为 0,并且满足 ∣ b i ∣ 总 和 ≤ 1 e 9 , b i ≠ 0 |bi| 总和 ≤ 1e9,bi≠0 bi1e9bi=0

思路:

设数组a:a b c d e f …

对于 n 为偶数:
那么为了使得 a i ∗ b i ai*bi aibi 总和为 0,可以两两配对,让这两两相加就 0。总和自然也为 0。
如何构造让这两两相加为 0 呢?对于 相 邻 位 置 元 素 a , b 相邻位置元素a,b a,b,可以构造第一个为 b b b,第二个为 − a -a a
a ∗ b + b ∗ ( − a ) = 0 a*b + b*(-a) = 0 ab+b(a)=0

对于 n 为奇数:
那么就先让前 n − 3 n-3 n3 个数,肯定为偶数个,两两配对,使其总和为0。
然后构造让最后剩下的 3 个相乘总和为 0。
对于最后三个数 x , y , z x,y,z x,y,z,可以构造 − z , − z , x + y -z,-z,x+y z,z,x+y
x ∗ ( − z ) + y ∗ ( − z ) + z ∗ ( x + y ) = 0 x*(-z) + y*(-z) + z*(x+y) = 0 x(z)+y(z)+z(x+y)=0
但是,b 数组中元素不能为 0,所以要选择两个相加不为 0 的数充当 x + y x+y x+y

Code:

const int N = 200010;
int T, n, m, a[N];int main(){Ios;cin>>T;while(T--){cin>>n;for(int i=1;i<=n;i++) cin>>a[i];if(n%2==0){for(int i=1;i<=n;i++){if(i%2) cout<<a[i+1]<<" ";else cout<<-a[i-1]<<" ";}}else{for(int i=1;i<=n-3;i++){if(i%2) cout<<a[i+1]<<" ";else cout<<-a[i-1]<<" ";}int x=a[n-2],y=a[n-1],z=a[n];if(x+y!=0) cout<<-z<<" "<<-z<<" "<<x+y;else if(x+z!=0) cout<<-y<<" "<<x+z<<" "<<-y;else cout<<y+z<<" "<<-x<<" "<<-x;}cout<<endl;}return 0;
}

今天是1024哇~


http://www.ppmy.cn/news/120237.html

相关文章

Codeforces Round #750 (Div. 2) - B. Luntik and Subsequences - 题解

目录 Codeforces Round #750 (Div. 2) - B. Luntik and SubsequencesProblem DescriptionInputSample InputSample OnputNote 题目大意解题思路AC代码 Codeforces Round #750 (Div. 2) - B. Luntik and Subsequences 传送门 Time Limit: 1 seconds Memory Limit: 256 megabyte…

性能分析之TPS从300到750的过程

文章目录 背景问题1&#xff1a;TPS呈锯齿状&#xff0c;忽高忽低问题2&#xff1a;调整数据库参数问题3&#xff1a;网络队列问题4&#xff1a;网络带宽不足问题5&#xff1a;数据问题结论 背景 前几天在 7DGroup 的群中&#xff0c;小鹏同学提了一个问题。 群里一顿讨论。终…

STM32H743/750+Cube+DP83848(一)

首个菜鸟博客&#xff0c;大哥们轻点喷 上重点&#xff1a;开发环境不管是CubeIDE&#xff08;IDE生成的程序只能IDE编译&#xff09;还是CubeMX&#xff08;它只是生成工具&#xff0c;不能编译&#xff0c;要用MDK或者IAR等&#xff0c;吐槽一下&#xff0c;MX生成后很多用不…

DMS感知方案前装赛道「排位」,2025年750万辆市场争夺

对舱内驾驶员、乘客的关怀&#xff0c;正在成为车企新一轮体验升级的关键突破口。在2023年CES展上&#xff0c;类似的产品方案也成为汽车行业的焦点。 比如&#xff0c;一家名为Myant的创新材料技术公司&#xff0c;在今年CES期间推出了一款将传感器和执行器&#xff08;与编织…

Swift AsyncSequence — 代码实例详解

文章目录 前言什么是 AsyncSequence?创建 AsyncSequence异步序列的迭代结论 前言 AsyncSequence 是并发性框架和 SE-298 提案的一部分。它的名字意味着它是一个提供异步、顺序和迭代访问其元素的类型。换句话说&#xff1a;它是我们在 Swift 中熟悉的常规序列的一个异步变体。…

50-75

数组 概念&#xff1a;数据的集合 数据类型分类 创建数组&#xff1a;[] push 在数组末尾追加一个元素 pop 用来删除数组最后一个元素 unshift 向数组开头添加一个或者多个元素&#xff0c;并返回新的新租长度 shift 可以删除数组的第一个元素&#xff0c;并将删除的作为返…

linux chmod 755 ,750,777设置原理

chmod是Linux下设置文件夹权限的命令&#xff0c;后面一般跟三个数据&#xff0c;代表不用用户群体在这个文件夹上的权限设置&#xff1a; 一般是三个数字&#xff1a; chmod 750 dir_wzg 第一个数字表示文件所有者的权限 第二个数字表示文件所有者同属一个用户组的其他用户在…

出现Permission denied的解决办法(750权限谨慎使用)

如果不明白其中的含义 请勿使用此命令 提示 Permission denied 解决的办法&#xff1a; // 注意&#xff1a;777权限谨慎使用 为高权限 $ sudo chmod -R xxx 某一目录// 自己定义xxx&#xff0c;下面有说明 其中 -R 是指级联应用到目录里的所有子目录和文件 750 表示文件…