欢迎访问 生活随笔!

生活随笔

当前位置: 首页 >

牛客练习赛52-记录

发布时间:2023/12/3 44 豆豆
生活随笔 收集整理的这篇文章主要介绍了 牛客练习赛52-记录 小编觉得挺不错的,现在分享给大家,帮大家做个参考.

正题

比赛链接:https://ac.nowcoder.com/acm/contest/1084#question


成绩


T1:T1:T1:数数

题目大意

给出nnn,求∑i=1n∑j=1n(i∗j)\sum_{i=1}^n \sum_{j=1}^n (i*j)i=1nj=1n(ij)

∏i=1n∏j=1n(i∗j)\prod_{i=1}^n\prod_{j=1}^n(i*j)i=1nj=1n(ij)

解题思路

第一个答案显然就是
(∑i=1ni)∗(∑j=1nj)(\sum_{i=1}^ni)*(\sum_{j=1}^n j)(i=1ni)(j=1nj)
等差数列求和即可O(1)O(1)O(1)解决。
第二个是
∏i=1ni2n⇒(∏i=1ni)2n\prod_{i=1}^ni^{2n} \Rightarrow\ (\prod_{i=1}^n i)^{2n}i=1ni2n (i=1ni)2n
预处理后O(log⁡n)O(\log n)O(logn)回答。

codecodecode

#include<cstdio> #include<cstring> #include<algorithm> #define ll long long using namespace std; const ll XJQ=998244353; ll t,n,s[10010000],sum; ll power(ll x,ll b) {ll ans=1;while(b){if(b&1) ans=ans*x%XJQ;x=x*x%XJQ;b>>=1;}return ans; } int main() {scanf("%lld",&t);s[0]=1;for(ll i=1;i<=1e7;i++)s[i]=s[i-1]*i%XJQ;while(t--){scanf("%lld",&n);sum=((n+1)*n/2)%XJQ;printf("%lld %lld\n",sum*sum%XJQ,power(s[n],2*n));} }

T2:GalahadT2:GalahadT2:Galahad

题目大意

一个长度为nnn的序列,求[l,r][l,r][l,r]这个区间的和,需要注意的是若一个数出现多次的话只计算一次。

解题思路

莫队会T\color{red}\texttt{\huge莫队会T}莫队会T
我们先将询问按照右端点单调不降排序,然后我们用指针进行扫描。

现在我们不需要考虑右端点了,只需要在已有的数中每次询问一个左端点。

我们考虑如何计算,因为不能重复,我们可以对于每个数计算出一个可以影响的范围,也就是最右边的那个数。

我们现在得出一种算法,我们每次右端点移动时加入一个数,若这个数之前没有就直接在树状数组上加入,否则就将前面的那个赋值为0后再进行加入。

codecodecode

#include<cstdio> #include<cstring> #include<algorithm> #define lowbit(x) (x&-x) #define ll long long using namespace std; const ll N=5e5+100; struct node{ll l,r,id; }a[N]; ll n,m,w[N],t[N],ans[N],v[N],sum; void change(ll x,ll z) {while(x<=n){t[x]+=z;x+=lowbit(x);} } ll ask(ll x) {ll ans=0;while(x){ans+=t[x];x-=lowbit(x);}return ans; } bool cMp(node x,node y) {return x.r<y.r;} int main() {scanf("%lld%lld",&n,&m);for(ll i=1;i<=n;i++)scanf("%lld",&w[i]);for(ll i=1;i<=m;i++)scanf("%lld%lld",&a[i].l,&a[i].r),a[i].id=i;sort(a+1,a+1+m,cMp);ll tail=1;for(ll i=1;i<=m;i++){while(tail<=a[i].r){if(v[w[tail]]) change(v[w[tail]],-w[tail]);else sum+=w[tail];v[w[tail]]=tail;change(tail,w[tail]);tail++;}ans[a[i].id]=sum-ask(a[i].l-1);}for(ll i=1;i<=m;i++)printf("%lld\n",ans[i]); }

T3:T3:T3:烹饪

题目大意

nnn个数的序列aaa,在其中选出若干个组成无序序列bbb。使得N+∈∑(bi∗ki)\mathbb{N}^+\in \sum (b_i*k_i)N+(biki)
kik_iki为任意整数。

求有多少种选择方案数。

解题思路

根据裴蜀定理,我们有ax+by=gcd(a,b)ax+by=gcd(a,b)ax+by=gcd(a,b),若gcd(a,b)=1gcd(a,b)=1gcd(a,b)=1那么就可以变成任意正整数。我们可以将其扩展到多元。
gcd(a,b)x+cy=gcd(a,b,c)⇒ax+by+cz=gcd(a,b,c)gcd(a,b)x+cy=gcd(a,b,c)\Rightarrow ax+by+cz=gcd(a,b,c)gcd(a,b)x+cy=gcd(a,b,c)ax+by+cz=gcd(a,b,c)
以此类推我们可以得出若我们选择的无序序列bbbgcd=1gcd=1gcd=1那么就满足条件。

我们依次设立dpdpdp,设fi,jf_{i,j}fi,j表示到第iii个,gcdgcdgcd之和为jjj时的方案数。我们有
fi,gcd(i,j)=∑fi−1,jf_{i,gcd(i,j)}=\sum f_{i-1,j}fi,gcd(i,j)=fi1,j

这里我们倒过来转移即可,下面的代码是滚动了的。

codecodecode

#include<cstdio> #include<cstring> #include<algorithm> #define ll long long using namespace std; const ll XJQ=998244353; ll n,num,f[2100]; ll power(ll x,ll b) {ll ans=1;while(b){if(b&1) ans=ans*x%XJQ;x=x*x%XJQ;b>>=1;}return ans; } int main() {scanf("%lld",&n);for(ll i=1;i<=n;i++){scanf("%lld",&num);f[num]=(f[num]+1)%XJQ;for(ll j=1;j<=2000;j++)(f[__gcd(j,num)]+=f[j])%=XJQ;}printf("%lld",(f[1]*power(2,XJQ-2))%XJQ); }

T4:T4:T4:粉丝群

题目大意

求有多少个nnn个数的序列满足以下条件

  • 和为2n2n2n且每个数不小于1
  • 任意一个子集的和不为nnn
  • 求有多少个,和字典序第kkk小的方案的异或和。

    解题思路

    结论题,打表找一下就好了。
    我们会发现方案数是n−1n-1n1111和一个n+1n+1n+1,还有若是奇数的话还有一个全是222的方案。

    证明一下(十分感性),此时我们有一个长度为序列nnn,此时对于每个1≤ai≤n1\leq a_i\leq n1ain

    那么我们发现若一个数为2+k2+k2+k那么至少就会有kkk个数为111,假设最终能组成nnn的有lll个数那么有
    2l+∑i=1lki=n−z(z∈[0,∑i=1lk])2l+\sum_{i=1}^l k_i=n-z(z\in [0,\sum_{i=1}^l k])2l+i=1lki=nz(z[0,i=1lk])
    ⇒∑i=1lki≥n−2l−∑i=1lk\Rightarrow \sum_{i=1}^l k_i\geq n-2l-\sum_{i=1}^l ki=1lkin2li=1lk∑i=1lki≤n−2l\sum_{i=1}^l k_i\leq n-2li=1lkin2l
    显然此时对于任意∑i=1lki&gt;0\sum_{i=1}^l k_i&gt;0i=1lki>0都有解

    codecodecode

    #include<cstdio> #include<cstring> #include<algorithm> #define ll long long using namespace std; ll n,k; int main() {scanf("%lld%lld",&n,&k);printf("%lld\n",n+(n&1)-(n==1));if(n&1) printf("%lld",(k==n)?2:(n+1));else printf("%lld",(n+1)^1); }

    总结

    以上是生活随笔为你收集整理的牛客练习赛52-记录的全部内容,希望文章能够帮你解决所遇到的问题。

    如果觉得生活随笔网站内容还不错,欢迎将生活随笔推荐给好友。