博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
CSU-2046: sequence
阅读量:5283 次
发布时间:2019-06-14

本文共 1411 字,大约阅读时间需要 4 分钟。

CSU-: sequence

Description

给出一个长度为N的正整数序列a,你有两种变换操作:

1.把数列中的某个数乘 2。
2.把数列中的所有数减 1。
现在你需要通过最少的变换操作把这个数列中的数全部变成 0。

Input

第一行一个N。下面 N 行,每行一个正整数 $ A_i $ 描述这个数列。1 <= n <=200000, 1 <= \(a _i\) <=\(10^9\)

Output

输出一行一个正整数,表示最少的变换次数。

Sample Input

212

Sample Output

3

题解

我们考虑一个例子\(a_1 = 2, a_2 = 1025\),需要多少次变换

首先假如\(a_1\)只变幻到1023那么a1和a2无法同时到0,那么\(a_1\)至少需要10次乘法变化,那么这10次什么时候乘呢,我们并不关心,但可以知道的是必然能够通过10次变换使\(a_1和a_2\)某一时刻相等,可以这么想,\(a_1\)先乘10次2变成2048然后可以减1可以减2...这样必然可以使\(a_1和a_2\)相等。

这样我们可以得出一个数要经过的乘法变化次数为它乘多少次2可以大于最大的数,把乘法和加法次数加起来即可

#include
#define maxn 200050using namespace std;inline int getnum() { int ans = 0; char c; int flag = 1; while (!isdigit(c = getchar()) && c != '-'); if (c == '-') flag = -1; else ans = c - '0'; while (isdigit(c = getchar())) ans = ans * 10 + c - '0'; return ans * flag;}long long a[maxn];long long fast_pow(int a, int b) { long long ans = 1; while (b) { if (b & 1) ans *= a; a *= a; b >>= 1; } return ans;}int main() { int n = getnum(); long long maxx = 0; for (int i = 1; i <= n; i++) { a[i] = getnum(); maxx = max(a[i], maxx); } long long ans = 0; for (int i = 1; i <= n; i++) { int tmp = int(log2(maxx / a[i])); if (a[i] * fast_pow(2, tmp) < maxx) tmp++; ans += tmp; } printf("%lld", ans + maxx); return 0;}

转载于:https://www.cnblogs.com/artoriax/p/10347077.html

你可能感兴趣的文章
C# 通过 Quartz .NET 实现 schedule job 的处理
查看>>
关于java之socket输入流输出流可否放在不同的线程里进行处理
查看>>
目前为止用过的最好的Json互转工具类ConvertJson
查看>>
Day13
查看>>
tensorflow saver简介+Demo with linear-model
查看>>
Luogu_4103 [HEOI2014]大工程
查看>>
Oracle——SQL基础
查看>>
项目置顶随笔
查看>>
Redis的安装与使用
查看>>
P1970 花匠
查看>>
java语言与java技术
查看>>
NOIP2016提高A组五校联考2总结
查看>>
iOS 项目的编译速度提高
查看>>
table中checkbox选择多行
查看>>
Magento开发文档(三):Magento控制器
查看>>
性能调优攻略
查看>>
ie6解决png图片透明问题
查看>>
瞬间的永恒
查看>>
2019-8-5 考试总结
查看>>
JS中实现字符串和数组的相互转化
查看>>