洛谷 P10320 勇气(Courage) 题解

文章讲述了如何通过数学分析和对数性质解决一个关于整数x和n的数学问题,涉及连续平方根变换,最终给出一个通用公式并提供了一个C++程序实现,强调了特判在解题中的重要性。
摘要由CSDN通过智能技术生成

P10320 勇气(Courage) 题解

题目传送门

题目大意

给定两个整数 x , n x,n x,n 和一种变换方式,要求求出最少经过多少次变换之后 x x x 的值不小于 2 n 2^n 2n

上面所提到的“变换方式”如果使用函数来进行刻画的话,其表达式为:

f ( x i ) = { x 2 , i = 1 ( f ( x i − 1 ) 2 ) 2 , i > 1 f(x_i)=\left\{ \begin{array}{rcl} x^2, & & & i=1\\ (\frac{f(x_{i-1})}{2})^2, & &&i > 1 \end{array} \right. f(xi)={x2,(2f(xi1))2,i=1i>1

其中, f ( x i ) f(x_i) f(xi) 代表的是经过第 i i i 次变换后得到的数值。

变换分析

首先,我们先在小范围内进行模拟计算,其初始值为 x x x。为了更加直观的展示每组数据的由来,特地列出了原始的表达式和最后化简的表达式,如下表所示:

变换次数原始表达式化简表达式
0 0 0 x x x x x x
1 1 1 ( x 2 0 ) 2 \left(\frac{x}{2^0}\right)^2 (20x)2 x 2 2 0 \frac{x^2}{2^0} 20x2
2 2 2 ( x 2 2 ) 2 \left(\frac{x^2}{2}\right)^2 (2x2)2 x 4 2 2 \frac{x^4}{2^2} 22x4
3 3 3 ( ( x 4 2 2 ) 2 ) 2 \left(\frac{\left(\frac{x^4}{2^2}\right)}{2}\right)^2 (2(22x4))2 x 8 2 6 \frac{x^8}{2^6} 26x8
4 4 4 ( ( x 8 2 6 ) 2 ) 2 \left(\frac{\left(\frac{x^8}{2^6}\right)}{2}\right)^2 (2(26x8))2 x 16 2 14 \frac{x^{16}}{2^{14}} 214x16

观察上面的格式特征,我们不妨记经过第 i i i 次变换后得到的结果为 x m 2 n \frac{x^m}{2^n} 2nxm。对 m , n m,n m,n 分别进行分析,如下所示:

i i i 1 1 1 2 2 2 3 3 3 4 4 4 5 5 5 … … …… …… k k k
m m m 2 2 2 4 4 4 8 8 8 16 16 16 32 32 32 … … …… …… 2 k 2^k 2k
n n n 0 0 0 2 2 2 6 6 6 14 14 14 30 30 30 … … …… …… 2 k − 2 2^k-2 2k2

通过上表,我们可以得到结果的一个通用表达式。记经过第 i i i 次变换后的结果为 x i x_i xi,则有:

x i = x 2 i 2 2 i − 2 x_i=\frac{x^{2^i}}{2^{2^i-2}} xi=22i2x2i

题目分析

截至目前,我们已经得出了对于题目给定的变换方法的通式:

x i = x 2 i 2 2 i − 2 x_i=\frac{x^{2^i}}{2^{2^i-2}} xi=22i2x2i

由于题目要求的是一个最小的正整数 k k k,使得经过 k k k 次变换后得到的答案大于 2 n 2^n 2n,于是就会有下面的不等式:

x 2 k 2 2 k − 2 ≥ 2 n \frac{x^{2^k}}{2^{2^k-2}} \geq 2^n 22k2x2k2n

这时,我想到了高中数学中的对数,其中有一条定理:

对于一个不等式 m ≥ n m \geq n mn,将其两边同时取以同一数字为底的对数之后,不等号方向不变,即满足 log ⁡ k m ≥ log ⁡ k n \log_k{m} \geq \log_k{n} logkmlogkn

上述结论可以利用对数函数的单调性证明,在这里不过多阐述。所以对于这道题,由代数知识可有如下推导过程,应该是足够详细了:

x 2 k 2 2 k − 2 ≥ 2 n \frac{x^{2^k}}{2^{2^k-2}} \geq 2^n 22k2x2k2n

x 2 k ≥ 2 n × 2 2 k − 2 x^{2^k} \geq 2^n \times {2^{2^k-2}} x2k2n×22k2

x 2 k ≥ 2 n + 2 k − 2 x^{2^k} \geq 2^{n+2^k-2} x2k2n+2k2

l o g 2 x 2 k ≥ l o g 2 2 n + 2 k − 2 log_2{x^{2^k} }\geq log_2{2^{n+2^k-2}} log2x2klog22n+2k2

2 k l o g 2 x ≥ ( n + 2 k − 2 ) × l o g 2 2 2^klog_2{x}\geq (n+2^k-2) \times log_2{2} 2klog2x(n+2k2)×log22

2 k l o g 2 x ≥ n + 2 k − 2 2^k log_2{x}\geq n+2^k-2 2klog2xn+2k2

2 k l o g 2 x − 2 k ≥ n − 2 2^k log_2{x} - 2^k \geq n - 2 2klog2x2kn2

2 k ≥ n − 2 l o g 2 x − 1 2^k \geq \frac{n-2}{ log_2{x} -1} 2klog2x1n2

k ≥ l o g 2 n − 2 l o g 2 x − 1 k \geq log_2{\frac{n-2}{ log_2{x} -1}} klog2log2x1n2

看到这里,终于是拨开云雾了。经过我们的推导,发现对于给定的 x , n x,n x,n,在一般情况下,程序只要输出一个
⌈ l o g 2 n − 2 l o g 2 x − 1 ⌉ \lceil log_2{\frac{n-2}{ log_2{x} -1}} \rceil log2log2x1n2 即可。

参考代码

#include<bits/stdc++.h>
using namespace std;
int x, n;
int main() {
	cin >> x >> n;
	if(x==2&&n==2){
		cout<<1<<endl;
		return 0;
	}
	if (x == 2 && n > 2) {
		cout << "inf" << endl;
		return 0;
	}
	if (x >= pow(2, n)) {
		cout << 0 << endl;
		return 0;
	}
	if (log2((n - 2) / (log2(x) - 1))< 0) {
		cout << "inf" << endl;
		return 0;
	}
	cout << ceil(log2((n - 2) / (log2(x) - 1))) << endl;
	return 0;
}

这道题特判特别多,所以很考验我们对细节的理解,选手们要多加注意。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值