牛客 周赛82 20250227

news/2025/3/3 21:58:05/文章来源:https://www.cnblogs.com/dianman/p/18746440

牛客 周赛82 20250227

https://ac.nowcoder.com/acm/contest/102303

A:
题目大意:给定字符串 \(s\) ,判断首尾是否相同

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;int main()
{string s;cin>>s;if(s[0]==s[s.size()-1]) cout<<"YES";else cout<<"NO";	return 0;
}

简单签到

B:

题目大意:

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;int n;
int a[1010];int main()
{cin>>n;for (int i=1;i<=n;i++) cin>>a[i];sort(a+1,a+1+n);for (int i=2;i<=n;i++){if (a[i]==a[i-1]){cout<<"NO";return 0;}}cout<<"YES";return 0;
}

将窗口人数从小到大排序,当且仅当 \(a_{i+1}>a_i\) 时才能保证有充足的时间进行拍照操作

C:

题目大意:与B题共享背景,数据范围增大且需要输出排队路径

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;struct node{int t,pos;
};int n;
vector<node> a;int main()
{cin>>n;for (int i=1;i<=n;i++){int x;cin>>x;a.push_back({x,i});}sort(a.begin(),a.end(),[](node x,node y){return x.t<y.t;});for (int i=1;i<n;i++){if (a[i].t==a[i-1].t){cout<<"NO";return 0;}}cout<<"YES"<<endl;for (auto iter:a)cout<<iter.pos<<' ';return 0;
}

将每个窗口的编号与人数绑定,按照人数排序后,与B题类似的进行操作,最后输出窗口编号即可

D:
题目大意:有一个 \([1,n]\) 的排列,现在给出确定前缀最小值数组 \(a\) ,计算满足这个前缀最小值数组的排列个数

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;const int mod=998244353;void solve(void){int n;cin>>n;vector<int> a(n+10);for (int i=1;i<=n;i++) cin>>a[i];a[0]=1e9;LL ans=1;int now=n-a[1];for (int i=2;i<=n;i++){if (a[i]>a[i-1]){cout<<0<<endl;return;}if (a[i]==a[i-1]){ans=ans*now%mod;now--;}if (a[i]<a[i-1]){now+=a[i-1]-a[i]-1;}ans%=mod;}cout<<ans<<endl;
}int main()
{Trd;return 0;
}

前缀最小值数组的性质存在: \(a_{i}<a_{i-1}\implies\) 可以确定填在 \(i\) 位置上的数为 \(a_i\)

所以根据 \(a_i\) ,考虑每个位置上的数能选取的数字个数

初始化时,now=n-a[1] ,即从第二位开始考虑,能选的数字个数

  • a[i]>a[i-1] 显然不能构成一个正确的排列,输出 \(0\)

  • a[i]==a[i-1] 当前位置上没有确定数字,那么从可选的数字中取一个填入,对答案的贡献根据乘法原理,ans=ans*now

  • a[i]<a[i-1] 当前位置可以确定一个数,更新可选的数 now+=a[i-1]-a[i]-1

巧妙的是,过程中如果某一位无数可选那么对应的 \(now=0\) ,所以 \(ans\times0=0\) ,最后输出答案同样为 \(0\) ,符合题意

E:

题目大意:给定 \(n\) 个元素的两个数组 \(a,b\) ,从小到大选取 \(2\times m\le n\) 个下标,计算对于所有的下标组合得出的表达式的最小值

\[a_{i_1}+a_{i_2}+\cdots+a_{i_m}+b_{i_{m+1}}+b_{i_{m+2}}+\cdots+b_{i_{2*m}} \]

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;int main()
{int n,m;cin>>n>>m;priority_queue<int> qa;LL suma=0;vector<LL> pa(n+10);for (int i=1;i<=n;i++){int a;cin>>a;if(i<=m){qa.push(a);suma+=1ll*a;}else{if (a<qa.top()){suma-=qa.top();qa.pop();qa.push(a);suma+=a;}}if (i>=m)pa[i]=suma;}vector<int> b(n+10);for (int i=1;i<=n;i++) cin>>b[i];priority_queue<int> qb;LL sumb=0;vector<LL> pb(n+10);for (int i=n;i>=1;i--){if (i>=n-m+1){qb.push(b[i]);sumb+=1ll*b[i];}else{if (b[i]<qb.top()){sumb-=qb.top();qb.pop();qb.push(b[i]);sumb+=b[i];}}if (i<=n-m+1)pb[i]=sumb;}LL ans=LLinf;for (int i=m;i<=n-m;i++)ans=min(ans,pa[i]+pb[i+1]);cout<<ans;return 0;
}

预处理+堆优化

因为 $2\times m\le n\iff m\le \frac{n}{2} $,所以需要选取的 \(a_{i_1}+a_{i_2}+\cdots+a_{i_m}+b_{i_{m+1}}+b_{i_{m+2}}+\cdots+b_{i_{2*m}}\) 可以看作在 \(a\) 中选 \(m\) 个元素,在 \(b\) 中从 \(m+1\) 的下标开始再选 \(m\) 个元素

可以这样对称地来看

\[\overbrace{a_1,a_2,\cdots,a_i}^{{\rm{count}}\ m},\cdots a_{n-1},a_n \\ b_1,b_2,\cdots,\overbrace{b_{i+1},\cdots b_{n-1},b_n}^{{\rm{count}}\ m} \]

于是可以预处理出 \(a\) 数组前 \(i\) 个元素选出 \(m\) 个元素的最小和,以及 \(b\) 数组后 \(i\) 个元素选出 \(m\) 个元素的最小和

采用优先队列大根堆优化,注意边界情况

if(i<=m){qa.push(a);suma+=1ll*a;
}//在a中选,只有i>m后才有意义if (i>=m)pa[i]=suma;
//边界情况,i=m时也需要记录

最后的答案

for (int i=m;i<=n-m;i++)ans=min(ans,pa[i]+pb[i+1]);

枚举 \(i_m\) 分界线,范围在 \([m,n-m]\) 内,记录所需最小值即可

F:

题目大意:给定 \(n\) ,存在数组满足数组内每一个元素都是 \([1,n]\) 之间的整数,并且数组的每一个非空连续子区间都至少存在一个 "唯一元素" ,现构造一个由 \(n\) 个元素组成的、"种类数" 最少的这类数组

*唯一元素:定义一个非空数组的 "唯一元素" 为该数组中只出现一次的元素。一个数组可能有多个 "唯一元素" 、也可能没有 "唯一元素"

*种类数:定义一个数组的 "种类数" 为该数组中不同的元素个数

#include<bits/stdc++.h>
#define cintie ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define Trd int T;cin>>T;while (T--)solve();
#define LLinf 9e18;
#define Iinf 2e9
#define LL long long
#define Lc p<<1
#define Rc p<<1|1
#define lc(x) tr[x].ch[0]
#define rc(x) tr[x].ch[1]using namespace std;int main()
{int n;cin>>n;vector<int> a;a.push_back(1);int cnt=1;while (a.size()<n){vector<int> b;for (auto it:a) b.push_back(it);bool f=0;//标记是否到nfor (int i=0;i<b.size()-1;i++){if (a.size()==n){f=1;break;}a.push_back(b[i]);//类似倍增的构造}if (f) break;a.push_back(++cnt);//修改最后的字符}cout<<cnt<<endl;for (auto it:a) cout<<it<<' ';return 0;
}

思维构造

构造数组,当其中一个连续数组跨度为偶数时,其中的元素一定存在惟一个

将这个连续数组抽象为 \(A+B\) ,那么 \(A,B\) 一定不相同,贪心地想需要种类数最少情况,所以只让 \(B\) 其中一个元素与 \(A\) 不同即可

例如

1
1 2
1 2 1 3
1 2 1 3 1 2 1 4
1 2 1 3 1 2 1 4 1 2 1 3 1 2 1 5 

\(B\) 除开最后一个字符与 \(A\) 不同,其他元素都可以由 \(A\) 复制过来,这样构造出的数组种类数一定最少,并且可以由前面的状态递推出

类似于倍增地计算,当 \(n\)\(2\) 的整数幂时,\(B\) 最后的字符需要修正为一个新元素

数据量是10^3,手动打表只需要10次

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/892291.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

002搜索框-搜索功能的实现

1、设置js的data值 给Zcpmingxi一个测试值 2、把 sousuo这个名字 绑定到wxml里面的 搜索框上 <inpu/>         是一个搜索框标签 type="text"        表示格式是文本格式 value="{{sousuo}}"    …

Spring面试知识

Spring优点 1.通过控制反转和依赖注入实现低耦合 2.面向切面编程,将业务逻辑和系统功能区分开来(日志记录、事务管理、安全性) 3.切面和模板可以减少板式代码 4.声明式事务的支持(@Translation)可以实现对事务代码的灵活管理,提高代码的质量和效率 5.多种内置的框架(Mybaties…

GVIM环境配置记录

背景 GVIM只用自带安装的软件,可以完成文本编辑的功能,不过很多开发者编写了很多插件,配合这些插件来做文字代码编辑,能很好地提高速度与效率 GVIM的配置环境,装机后只配置一次,很容易忘记,下次重装系统或者配新机时,又要重新查找相关资料 这里做一次记录,方便后续重新…

VIM环境配置记录

背景 VIM只用自带安装的软件,可以完成文本编辑的功能,不过很多开发者编写了很多插件,配合这些插件来做文字代码编辑,能很好地提高速度与效率 VIM的配置环境,装机后只配置一次,很容易忘记,下次重装系统或者配新机时,又要重新查找相关资料 这里做一次记录,方便后续重新配…

endnote 基础使用

因为工作的原因,综述格式统一使用endnote。一小时速成,可以满足基础的综述引用。 安装 安装的是endnote 21,这个界面感觉比较简洁。 EndNote 21 的安装包中有汉化补丁 "D:\Program Files (x86)\EndNote 21\安装包\Crack\汉化补丁.exe" 2024-11-18 Endnote21更新-…

Day1-Markdown学习笔记

MarkDown学习 标题 一个#然后空格加内容是一级标题,两个是二级标题,三个是三级标题 字体 hello world hello world *** hello world*** hello world 一对*加上内容是斜体,两对是加粗,三对是既加粗又斜体, 一对~是加横线,就是废弃的意思 引用引用别人的内容一个> 加…

2025-03-02 闲话

2025-03-02 闲话走进这里时,求是园欢迎您。离开时,它会说,再见。昨天十一点,从这里走上蒋墩路,过了马路,是夜晚的学军。周末不再灯火通明,只剩下校门口的主灯,照亮着蓝色匾额的威严。昨天发了点牢骚,2023 年时进这个校园,不需要预约,刷脸时能发现不只一个我在这里的…

Semantic Kernel:接入azure中的deepseek-r1

SemanticKernel已经支持deepseek-r1了,官方的Blog地址是https://devblogs.microsoft.com/semantic-kernel/using-deepseek-models-in-semantic-kernel,同时给出了接入的Demo,遗憾的是deepseek不支持API的充值,没有办法测试。办法总比困难多,正好微软现在支持在Azure部署de…

C#中的Channel

在 .NET 的异步编程中,System.Threading.Channels 提供了一种强大的方式来处理生产者-消费者模式,尤其是当我们要在不同的任务或服务之间传递数据时。这篇文章我们就来聊聊 UnboundedChannelOptions 和 BoundedChannelOptions 这两个类,以及它们的使用场景和区别。代码背景介…

Kimi/DeepSeek最新论文MoBA与NSA阅读

From:https://www.big-yellow-j.top/posts/2025/02/21/Kimi-DS-Paper.html DeepSeek最新论文:Native Sparse Attention: Hardware-Aligned and Natively Trainable Sparse Attention以及 Kimi最新论文MOBA: MIXTURE OF BLOCK ATTENTION FOR LONG-CONTEXT LLMS这几篇文章都是针…

Windows 剪贴板 编程原理引入

前言 不得不说上三休四的生活就是舒服,我都有精力提升自己了。 本文将基于自己在生活中遇到的现象进行探索,因此问题引入对自己较为重要,读者可以跳过。 文章主要探讨剪贴板格式问题,即下面的链接。https://learn.microsoft.com/zh-cn/windows/win32/dataxchg/standard-cli…