题目传送门(内部题1)


输入格式

第一行两个整数$n$,$k$,代表树苗的数量和最大看书的总长度。
第二行n个整数$a_i$,代表林先森希望每棵树苗的最终高度。


输出格式

一行一个整数,代表最大可能的d值。


样例

样例输入:

3 4

1 3 5

样例输出:

3


数据范围与提示

样例解释:
第$3$天林先森砍掉了第一和第二棵树苗,第$6$天林先森砍掉了第三棵树苗。总共砍树的长度为$(3-1)+(3-3)+(6-5)=3$米。可以证明更大的d值无法满足要求。

数据范围:

对于$20%$的数据,$a_i ≤ {5×10}^5$。

另有$20%$的数据,$k≤1$。

对于所有的数据,$1≤n≤100$,$0≤k≤{10}^{11}$,$1≤a_i≤{10}^9$。


题解

看到$k$很大,$n$很小,优先选择从$n$入手。

$20\%$算法:

暗中观察数据范围,有$20%$的数据$k≤1$,怎么办呢?

这个时候分为两种情况:

  $\alpha.k=0$,那么就是说我们每一次都要赶巧了在这棵树苗长到最终高度那一天砍掉,所以答案即为所有最终高度的最大公约数。

  $\beta,k=1$,因为n比较小,所以我们每次枚举树苗,将它的最终高度+1,然后再求所有树苗的最终高度的最大公约数,取最大值即可。

期望得分:$20$分。

实际得分:$20$分。

$40\%$算法:

开始推式子,设这个天数为$d$,那么砍掉树苗i的高度即为$\left \lceil \frac{a_i}{d} \right \rceil \times d$,那么,可以列出式子:

$\sum \limits_{i=1}^{n} \left \lceil \frac{a_i}{d} \right \rceil \times d - a_i \leqslant k$

移项得:$\sum \limits_{i=1}^{n} \left \lceil \frac{a_i}{d} \right \rceil \times d \leqslant k + \sum \limits_{i=1}^{n} a_i$

惊喜发现上面不等式右边是定值,于是我们设$k + \sum \limits_{i=1}^{n} a_i$为$C$,先让$d=1$,每次让$d++$,当$d \geqslant \min a_i + k$时,不可能在有答案,所以这就是$d$的上界。

期望多得分数:$10$分。

$100\%$算法:

显然,$40\%$时间复杂度还是不允许,但是我们发现,有的d没有必要枚举。

注意对于每个$a_i$,$\left \lceil \frac{a_i}{d} \right \rceil$只有$\sqrt{a_i}$种不同的取值,因此,$\sum \limits_{i=1}^{n}\left \lceil \frac{a_i}{d} \right \rceil$只有$n \times \sqrt{a_i}$种不同的取值,利用数论分块,可以知道下一个d为$\frac{C}{\left \lceil \frac{C}{d+1} \right \rceil}$。

时间复杂度:$O( \sqrt{(\min a_i + k) \times n})$。

期望得分:$100$分。

实际得分:$100$分。


代码时刻

$20\%$算法:

#include<bits/stdc++.h>
using namespace std;
int n,k;
long long a[1000001];
long long ans;
long long gcd(long long x,long long y)
{return y==0?x:gcd(y,x%y);}
int main()
{
scanf("%d%d",&n,&k);
for(int i=1;i<=n;i++)
scanf("%lld",&a[i]);
if(!k)//特判k==0
{
ans=a[1];
for(int i=2;i<=n;i++)
ans=gcd(ans,a[i]);
printf("%lld",ans);
}
if(k==1)//特判k==1
{
long long flag=a[2];
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
if(i!=j)flag=gcd(flag,a[j]);
else flag=gcd(flag,a[j]+1);//将它+1
}
ans=max(ans,flag);
flag=a[1];
}
printf("%lld",ans);
}
return 0;
}

$40\%$算法(记得加上上面代码的那一段):

#include<bits/stdc++.h>
using namespace std;
int n;
long long a[100001];
long long sigma;
long long ans;
int main()
{
scanf("%d%lld",&n,&sigma);
for(int i=1;i<=n;i++)
{
scanf("%lld",&a[i]);
sigma+=a[i];
}
for(long long d=1;d<=sigma;d++)
{
long long flag=0;
for(int i=1;i<=n;i++)
{
if(a[i]%d)flag+=(a[i]/d+1)*d;
else flag+=a[i];
}
if(flag<=sigma)ans=d;
}
printf("%lld",ans);
return 0;
}

$100\%$算法:

#include<bits/stdc++.h>
using namespace std;
int n;
long long k;
long long a[1000001];
long long sigma,maxn;
long long ans;
int main()
{
scanf("%d%lld",&n,&k);
sigma=k;
for(int i=1;i<=n;i++)
{
scanf("%lld",&a[i]);
sigma+=a[i];
maxn=max(maxn,a[i]);
}
maxn+=k;
long long d=1;
while(1)
{
long long flag=0;
for(int i=1;i<=n;i++)
{
if(a[i]%d)flag+=(a[i]/d+1)*d;
else flag+=a[i];
}
if(flag<=sigma)ans=d;
if(maxn<=d)break;//上界
d=sigma/(sigma/(d+1));//更新d
}
cout<<ans<<endl;
return 0;
}

rp++

[CSP-S模拟测试]:砍树(数学+模拟)的更多相关文章

  1. [CSP-S模拟测试]:最大值(数学+线段树)

    题目背景 $Maxtir$最喜欢最大值. 题目传送门(内部题128) 输入格式 第$1$行输入四个正整数$n,m,q$. 第$2$至$n+1$行中,第$i+1$行输入魔法晶石$i$的三种属性$(x_i ...

  2. [CSP-S模拟测试]:Equation(数学+树状数组)

    题目描述 有一棵$n$个点的以$1$为根的树,以及$n$个整数变量$x_i$.树上$i$的父亲是$f_i$,每条边$(i,f_i)$有一个权值$w_i$,表示一个方程$x_i+x_{f_i}=w_i$ ...

  3. [CSP-S模拟测试]:Race(数学+Trie树)

    题目描述 一年一度的运动会开始了.有$N$个选手参赛,第$i$个选手有一个能力值(保证$A[i]$两两不同),比赛一共进行了天.在第$j$天($0\leqslant j\leqslant 2^{m-1 ...

  4. [CSP-S模拟测试]:旅行(数学+线段树)

    题目传送门(内部题12) 输入格式 第一行,一个整数$n$,代表树的点数.第二行,$n$个整数,第$i$个整数是$B_i$,描述排列$B$.接下来$n−1$行,每行两个整数$u,v$,描述一条树边$( ...

  5. noip 2018.10.14 模拟赛 砍树

    数学问题... 根据题意,有: 移项,整理,得: 记 于是 那么 可以看到,最多只会有2*个取值(显而易见) 于是对应的,可能产生效果的d也只会有个,于是我们把他们找出来,扔进一个数组里然后排序,去重 ...

  6. [CSP-S模拟测试]:超级树(DP)

    题目传送门(内部题5) 输入格式 一行两个整数$k$.$mod$,意义见上. 输出格式 一行一个整数,代表答案. 样例 样例输入1: 2 100 样例输出1: 样例输入2: 3 1000 样例输出2: ...

  7. [CSP-S模拟测试]:不等式(数学)

    题目描述 小$z$热衷于数学.今天数学课的内容是解不等式:$L\leqslant S\times x\leqslant R$.小$z$心想这也太简单了,不禁陷入了深深的思考:假如已知$L,R,S,M$ ...

  8. [CSP-S模拟测试]:A(数学)

    题目传送门(内部题44) 输入格式 一行四个整数,分别表示$S,T,a,b$. 输出格式 输出最小步数,数据保证有解. 样例 样例输入: 10 28 4 2 样例输出: 数据范围与提示 样例解释: 先 ...

  9. [CSP-S模拟测试]:装饰(数学)

    题目传送门(内部题147) 输入格式 每个测试点第一行一个正整数$T$,表示该测试点内的数据组数. 接下来$T$行,每行三个非负整数$a,b,c$,含义如题目中所示. 输出格式 对每组数据输出一行一个 ...

随机推荐

  1. <<用法

    数据移位运算符,左移几位,如:x=i<<4;就是将i的值左移4位(放大2的4次方)后,赋给x,若i=2,则X=32.

  2. new 和 malloc 的区别 及使用

    Malloc: 定义上:malloc  memory allocation 动态内存分配 是c中的一个函数 使用方法: extern void *malloc(unsigned int num_byt ...

  3. 【监控笔记】【1.2】监控事件系列——SQL Trace(默认跟踪与自定义跟踪)

    目录: [1.1]概念与使用 [1.2]跟踪的基本操作 --[1.2.1]查看默认跟踪是否在运行 --[1.2.2]开启默认跟踪 --[1.2.3]关闭默认跟踪 --[1.2.4]查看跟踪文件/查看跟 ...

  4. kubernetes快速应用入门

    kubectl 就是 api server的客户端工具 创建一个nginx的pod [root@master ~]# kubectl run nginx-deploy --image=nginx:1. ...

  5. 数位dp相关

    经典的数位Dp是要求统计符合限制的数字的个数. 一般的形式是:求区间[n,m]满足限制f(1). f(2). f(3)等等的数字的数量是多少. 条件 f(i) 一般与数的大小无关,而与数的组成有关. ...

  6. java复习(4)异常

    1.Java异常的分类和类结构图 1.Throwable是整个java异常体系的超类,所有的异常类都派生自这个类,包含Error和Exception这两个直接的子类,概括了所有能被当做异常跑出来的东西 ...

  7. js/nodejs导入Excel相关

    导入示例如下: Excel可设置单元格的数字显示格式,特别的,常规格式下,会根据列宽缩进显示. 实际中,有时需要导入实际值,有时需要导入显示值. 而B2的显示值,由于跟列宽相关,目前未找到任何软件,可 ...

  8. 使用Docker搭建Jumpserver堡垒机

    使用Docker搭建Jumpserver堡垒机 1.环境准备 操作系统:CentOS 7.6.1810 软件源:阿里云镜像 #内核版本(Docker 要求 CentOS 系统的内核版本高于 3.10) ...

  9. 安信可ESP-12F(8266)模块烧录问题解决:示 :ESP8266 Chip stub error esp_stub_an

    模块:安信可ESP-12F, 8266模块 1. 供电电流大于500ma,网上买的串口工具供电电流都是不行的,要上主电源,或者外接电源. 2. 焊接在主板上的模块由于串口同时连接了MCU的串口,如果M ...

  10. 001-supervisor

    supervisor 使用教程(转) 原文地址:https://word.gw1770df.cc/2016-08-04/linux/supervisor-%E4%BD%BF%E7%94%A8%E6%9 ...