前言

先吐槽一下出题人,T2 牛马数据连棵树都不是。。

T3 描述不清楚。。

T1 如何优雅的送分

解题思路

我考场上还真以为是个送分题,然而。。。

莫比乌斯反演。。。

对于一个数字 n 有 \(2^{F(n)}=\sum\limits_{d|n}\mu^2(d)\) ,由于有平方因子的数字的 \(\mu\) 的值是 0 ,就相当于在所有的质因数里面选择若干个质因数组合。

\(\mu^2(n)=\sum\limits_{d^2|n}\mu(d)\) 对于质数的情况是比较显然的,毕竟符合条件的只有 1 。

这个可以理解为枚举质因数的个数算对应的答案。

假设这个数质因数的个数是 \(cnt\) ,那么答案就是 \(\sum\limits_{i=0}^{cnt}(-1)^i\times \binom{cnt}{i}\) 由二项式定理可得上式为 0 。

于是答案就是 \(\displaystyle\sum_{i=1}^n 2^{F(i)}=\sum_{i=1}^n\sum_{d|i}\sum_{k^2|d}\mu(k)\)

更改枚举顺序 \(\displaystyle\sum_{k=1}^n\mu(k)\sum_{k^2|d}\lfloor\frac{n}{d}\rfloor\)

也就是 \(\displaystyle\sum_{k=1}^n\mu(k)\sum_{i=1}^{\lfloor\frac{n}{k^2}\rfloor}\lfloor\frac{n}{k^2i}\rfloor\)

设 \(S(n)=\sum\limits_{i=1}^n\lfloor \frac{n}{i}\rfloor\) 上述柿子就是 \(\sum\limits_{k=1}^n \mu(k)S(\lfloor\frac{n}{k^2}\rfloor)\) 。

对于 \(S\) 的运算可以数论分块 复杂度是 \(\mathcal{O}(\sqrt{n}logn)\)

code

#include <bits/stdc++.h>
#define int long long
#define ull unsigned long long
#define f() cout<<"Failed"<<endl
using namespace std;
inline int read()
{
int x=0,f=1;char ch=getchar();
while(ch>'9'||ch<'0'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*f;
}
const int N=1e6+7,mod=1e9+7;
int n,m,ans,cnt,pri[N],mu[N];
bool vis[N];
void Pre_work()
{
mu[1]=1;
for(int i=2;i<=m;i++)
{
if(!vis[i]) pri[++cnt]=i,mu[i]=-1;
for(int j=1;j<=cnt&&pri[j]*i<=m;j++)
{
int temp=i*pri[j]; vis[temp]=true;
if(i%pri[j]==0){mu[temp]=0;break;}
mu[temp]=-mu[i];
}
}
}
int S(int lim)
{
int sum=0;
for(int l=1,r;l<=lim;l=r+1)
{
r=lim/(lim/l);
sum=(sum+lim/l%mod*(r-l+1)%mod)%mod;
}
return sum;
}
signed main()
{
freopen("elegant.in","r",stdin); freopen("elegant.out","w",stdout);
n=read(); m=sqrt(n)+1; Pre_work();
for(int i=1;i<=n;i++)
{
int temp=S(n/(i*i));
if(!temp) break;
ans=(ans+mu[i]*temp%mod+mod)%mod;
}
printf("%lld",ans);
return 0;
}

T2 阴阳

解题思路

正解不太会,打了个暴力,可能是由于数据水,骗到了 100pts (虽然后来被Hack成了 91pts)

比较好奇的就是出题人的数据怎么造的(原来 n 个点 n-1 条边还可以是有环的森林。。。)

暴力思路比较简洁,我们需要一个可以动态开空间并且支持查找并且删掉某一个值的数据结构,unoedered_set 刚好可以满足我们的需求。

于是我们可以维护每一个版本的所有黑色节点,每次暴扫整个 set 求出答案。

code

#include <bits/stdc++.h>
#define int long long
#define ull unsigned long long
#define f() cout<<"Failed"<<endl
using namespace std;
inline int read()
{
int x=0,f=1;char ch=getchar();
while(ch>'9'||ch<'0'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*f;
}
const int N=1e5+10,M=3e3+10,INF=1e9;
int typ,n,m,t,ans,cnt,now,s[N];
int tot=1,head[N],ver[N<<1],nxt[N<<1];
int tim,dfn[N],siz[N],fa[N],son[N],dep[N],topp[N];
unordered_set<int> res[N];
void add_edge(int x,int y)
{
ver[++tot]=y;
nxt[tot]=head[x];
head[x]=tot;
}
void dfs1(int x)
{
siz[x]=1;
for(int i=head[x];i;i=nxt[i])
{
int to=ver[i]; if(siz[to]) continue;
fa[to]=x; dep[to]=dep[x]+1;
dfs1(to); siz[x]+=siz[to];
if(siz[to]>siz[son[x]]) son[x]=to;
}
}
void dfs2(int x,int tp)
{
topp[x]=tp; dfn[x]=++tim;
if(son[x]) dfs2(son[x],tp);
for(int i=head[x];i;i=nxt[i])
if(!dfn[ver[i]])
dfs2(ver[i],ver[i]);
}
int LCA(int x,int y)
{
while(topp[x]^topp[y])
{
if(dep[topp[x]]<dep[topp[y]]) swap(x,y);
x=fa[topp[x]];
}
if(dep[x]>dep[y]) swap(x,y);
return x;
}
int dist(int x,int y){return dep[x]+dep[y]-2*dep[LCA(x,y)];}
signed main()
{
freopen("yygq.in","r",stdin); freopen("yygq.out","w",stdout);
typ=read(); n=read();
for(int i=1,x,y;i<n;i++)
x=read(),y=read(),
add_edge(x,y),add_edge(y,x);
dfs1(1); dfs2(1,1); m=read();
while(m--)
{
int opt,x; opt=read(); x=read()^(typ*ans);
if(opt==1)
{
cnt++; res[cnt]=res[now];
if(res[now].find(x)==res[now].end()) res[cnt].insert(x);
else res[cnt].erase(x); now=cnt; continue;
}
if(opt==2)
{
ans=INF;
for(auto it:res[now]) ans=min(ans,dist(x,it));
printf("%lld\n",ans); continue;
}
now=x;
}
return 0;
}

T3 你猜是不是找规律

解题思路

我还真就以为是个找规律了。。。

出题人描述不清楚,题目认为的有序序列只是一种顺序只能是升序或者只能是降序。

DP 转移 \(f_{i,j}\) 表示对于有序的序列前 i 个数字交换 j 次可以得到的不同序列。

就有方程:\(f_{i,j}=f_{i-1,j}+f_{i-1,j-1}\times(i-1)\) 。

然后发现其实前缀和是一个有 \(2k\) 项的多项式(我也不知道为啥是这个。。),然后直接拉格朗日插值。。

code

#include <bits/stdc++.h>
#define int long long
#define ull unsigned long long
#define f() cout<<"Failed"<<endl
using namespace std;
inline int read()
{
int x=0,f=1;char ch=getchar();
while(ch>'9'||ch<'0'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*f;
}
const int N=3e3+10,mod=1e9+7;
int n,m,ans,f[2][N],s[N<<1];
int power(int x,int y,int p=mod)
{
int temp=1;
while(y)
{
if(y&1) temp=temp*x%p;
x=x*x%p; y>>=1;
}
return temp;
}
void solve1()
{
for(int i=1;i<=n;i++)
{
for(int j=0;j<=m;j++) f[i&1][j]=f[(i&1)^1][j];
for(int j=1;j<=min(i,m);j++) f[i&1][j]=(f[i&1][j]+(i-1)*f[(i&1)^1][j-1])%mod;
}
for(int i=0;i<=m;i++) ans=(ans+f[n&1][i])%mod;
printf("%lld",ans); exit(0);
}
signed main()
{
freopen("guess.in","r",stdin); freopen("guess.out","w",stdout);
n=read(); m=read(); f[0][0]=1;
if(n<=3000) solve1();
for(int i=1;i<=2*m+1;i++)
{
for(int j=0;j<=m;j++) f[i&1][j]=f[(i&1)^1][j];
for(int j=1;j<=min(i,m);j++)
f[i&1][j]=(f[i&1][j]+(i-1)*f[(i&1)^1][j-1])%mod;
for(int j=0;j<=m;j++) s[i]=(s[i]+f[i&1][j])%mod;
}
for(int i=1;i<=2*m+1;i++)
{
int temp=1,base=1;
for(int j=1;j<=2*m+1;j++)
if(i!=j)
temp=(n-j+mod)%mod*temp%mod,
base=base*(i-j+mod)%mod;
ans=(ans+s[i]*temp%mod*power(base,mod-2))%mod;
}
printf("%lld",ans);
return 0;
}

T4 小说

解题思路

运用退背包每次枚举退掉的点,选择造成损失比较小的,方案可以在对于大质数取模的意义下考虑。

然后有了这个去掉的物品,接下来我们所选择的 b 不可以被剩下物品 \(v_i,-v_i\) 构成。

对于剩下的物品按上面两个值做一个 01背包,取大于 0 的第一个值作为答案。

code

#include <bits/stdc++.h>
#define int long long
#define ull unsigned long long
#define f() cout<<"Failed"<<endl
using namespace std;
inline int read()
{
int x=0,f=1;char ch=getchar();
while(ch>'9'||ch<'0'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*f;
}
const int N=110,M=7e5+10,mod=1e9+7,base=7e5+10;
int n,lim,ans,maxn,id,s[N],f[M],g[M];
bitset<(M<<1)> bit;
signed main()
{
freopen("novel.in","r",stdin); freopen("novel.out","w",stdout);
n=read(); f[0]=1; for(int i=1;i<=n;i++) s[i]=read(),lim+=s[i];
for(int i=1;i<=n;i++)
for(int j=lim;j>=s[i];j--)
f[j]=(f[j]+f[j-s[i]])%mod;
for(int i=1;i<=n;i++)
{
int sum=0;
for(int j=0;j<=lim;j++) g[j]=f[j];
for(int j=s[i];j<=lim;j++) g[j]=(g[j]-g[j-s[i]]+mod)%mod;
for(int j=1;j<=lim;j++) sum+=(g[j]>0);
if(sum>maxn) maxn=sum,id=i;
}
bit[base]=true;
for(int i=1;i<=n;i++) if(i!=id) bit|=bit>>s[i],bit|=bit<<s[i];
for(int i=1;i<=lim+1;i++) if(!bit[i+base]){ans=i;break;}
printf("%lld %lld",s[id],ans);
return 0;
}

NOIP模拟75的更多相关文章

  1. Noip模拟75 2021.10.12

    T1 如何优雅的送分 他说是送分题,我就刚,没刚出来,想到莫比乌斯容斥后就都没推出来 好吧还是不能被恶心的题目,挑衅的语言打乱做题节奏 于是这一场也就没了.... $F(i)$表示$i$的不同质因子集 ...

  2. 2021.10.12考试总结[NOIP模拟75]

    T1 如何优雅的送分 考虑式子的实际意义.\(2^{f_n}\)实际上就是枚举\(n\)质因子的子集.令\(k\)为这个子集中数的乘积,就可以将式子转化为枚举\(k\),计算\(k\)的贡献. 不难得 ...

  3. 2019.7.29 NOIP模拟测试10 反思总结【T2补全】

    这次意外考得不错…但是并没有太多厉害的地方,因为我只是打满了暴力[还没去推T3] 第一题折腾了一个小时,看了看时间先去写第二题了.第二题尝试了半天还是只写了三十分的暴力,然后看到第三题是期望,本能排斥 ...

  4. NOIP模拟17.9.22

    NOIP模拟17.9.22 前进![问题描述]数轴的原点上有一只青蛙.青蛙要跳到数轴上≥

  5. NOIP 模拟4 T2

    本题属于二和一问题 子问题相互对称 考虑对于问题一:知a求b 那么根据b数组定义式 显然能发现问题在于如何求dis(最短路) 有很多算法可供选择 dijsktra,floyed,bfs/dfs,spf ...

  6. NOIP模拟赛20161022

    NOIP模拟赛2016-10-22 题目名 东风谷早苗 西行寺幽幽子 琪露诺 上白泽慧音 源文件 robot.cpp/c/pas spring.cpp/c/pas iceroad.cpp/c/pas ...

  7. contesthunter暑假NOIP模拟赛第一场题解

    contesthunter暑假NOIP模拟赛#1题解: 第一题:杯具大派送 水题.枚举A,B的公约数即可. #include <algorithm> #include <cmath& ...

  8. NOIP模拟赛 by hzwer

    2015年10月04日NOIP模拟赛 by hzwer    (这是小奇=> 小奇挖矿2(mining) [题目背景] 小奇飞船的钻头开启了无限耐久+精准采集模式!这次它要将原矿运到泛光之源的矿 ...

  9. 大家AK杯 灰天飞雁NOIP模拟赛题解/数据/标程

    数据 http://files.cnblogs.com/htfy/data.zip 简要题解 桌球碰撞 纯模拟,注意一开始就在袋口和v=0的情况.v和坐标可以是小数.为保险起见最好用extended/ ...

  10. 队爷的讲学计划 CH Round #59 - OrzCC杯NOIP模拟赛day1

    题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的讲学计划 题解:刚开始理解题意理解了好半天,然后发 ...

随机推荐

  1. ImageJ使用教程(一):开始使用

    目录 简介 界面介绍 Edit->Options 开始使用 打开图片 放大拖拽 图片信息 色彩分析 保存图片 总结 参考文章 ImageJ软件 简介 ImageJ是一个基于java的公共的图像处 ...

  2. Unity性能优化——托管堆/GC

    了解托管堆 许多 Unity 开发者面临的另一个常见问题是托管堆的意外扩展.在 Unity 中,托管堆的扩展比收缩容易得多.此外,Unity 的垃圾收集策略往往会使内存碎片化,因此可能阻止大型堆的收缩 ...

  3. 力扣539(java)-最小时间差(中等)

    题目: 给定一个 24 小时制(小时:分钟 "HH:MM")的时间列表,找出列表中任意两个时间的最小时间差并以分钟数表示. 示例 1: 输入:timePoints = [" ...

  4. OPLG:新一代云原生可观测最佳实践

    ​简介:OPLG 体系拥有成熟且富有活力的开源社区生态,同时也经过了大量企业生产环境的实践检验,是当下建设新一代云原生统一可观测平台的热门选择.但是,OPLG 只是提供了一个技术体系,如何灵活运用,解 ...

  5. MySQL 深潜 - MDL 锁的实现与获取机制

    简介:本文将介绍在 MDL 系统中常用的数据结构及含义,然后从实现角度讨论 MDL 的获取机制与死锁检测,最后分享在实践中如何监控 MDL 状态. ​ 作者 | 泊歌 来源 | 阿里技术公众号 一 背 ...

  6. hyengine - 面向移动端的高性能通用编译/解释引擎

    ​简介:手机淘宝客户端在历史上接过多种多样的脚本引擎,用于支持的语言包括:js/python/wasm/lua,其中js引擎接过的就有:javascriptcore/duktape/v8/quickj ...

  7. Flink 和 Pulsar 的批流融合

    简介: 如何通过 Apache Pulsar 原生的存储计算分离的架构提供批流融合的基础,以及 Apache Pulsar 如何与 Flink 结合,实现批流一体的计算. 简介:StreamNativ ...

  8. 开源微服务编排框架:Netflix Conductor

    简介:本文主要介绍netflix conductor的基本概念和主要运行机制. ​ 作者 | 夜阳 来源 | 阿里技术公众号 本文主要介绍netflix conductor的基本概念和主要运行机制. ...

  9. [GPT] AI大模型背景下,小模型还有优势吗?

      在AI大模型背景下,小的模型仍然具有一些优势. 以下是一些可能的优势: 速度和效率:相比于大模型,小模型需要更少的计算资源和时间,能够更快地完成训练和预测,并且能够在较低的硬件配置上运行. 灵活性 ...

  10. [Trading] 专业交易: 专业交易员和散户交易员的不同, 什么是专业交易员

    专业交易员可能用的是公司的钱或者自己的钱 有基本工资支持,散户用的是自己的钱 没有人提供工资来做交易. 目标不同,专业交易员的目的是增长投资账户和获得奖金,散户大部分是为了提取盈利收入而无法增长投资账 ...