【Leetcode Daily】1922统计好数字的数目
题目浅析
- 想查看原题可以点击题目链接。
- 简单地说,就是给一个数字 n,要求给出满足特定要求的位数为 n 的数字个数,该要求是(从零开始)偶数下标为偶数且奇数下标为质数。
思路分享
- 刚开始本想用数位 dp,但细算觉着计算量还是太大,本地对于每一位实际上没有太多限制,但是总数量非常大,只好看看题解思路。
- 本题本质上可以用组合数学算出,一个 n 位的数字,必定有 (n/2) 取下位偶数下标,剩下奇数下标,偶数下标有 5 个可能,奇数下标有 4个可能,所以只要计算出 5^((n+1)/2) + 4^(n/2) 即可(这里的 / 为整除)。
- 注意,由于数字很大,有两个要点,一个是快速幂,二是如何正确取模。
快速幂
- 快速幂的本质是通过把普通的累乘,转化为平方乘积,复杂度由O(n)降到了O(log(n))。
- 比如,计算 2 的 13 次方,13 的二进制表示为 1101,2 的 13 次方可以视为 2^4 * 2^3 * 2^1。
- 转化为程序的自然语言,就是不断判断次方数的最后一位是否为 1,是的话,将结果乘上当前底数,每次次方数右移时,底数则平方。
- 如果指数为负数,则将指数取反得正数,同时把底数求倒数。
取模方法
- 这里涉及到不少离散数学的知识,简单地说,除了 python 以外的语言如果先求解结果再取模一般都会因为溢出出错。因此需要通过下面方法来解决。
- 对于加法 a + b,可以这么取模:a + b % MOD
- 对于减法 a - b,可以取模:(a - b + MOD ) % MOD
- 对于乘法 a*b*c, 可以取模:(a * b % MOD) * c % MOD
- 除法尚未理解,姑且放着,用到自然会学:)
https://leetcode.cn/discuss/post/3584387/fen-xiang-gun-mo-yun-suan-de-shi-jie-dan-7xgu/
代码解答(强烈建议自行解答后再看)
- 参考的解法
1 | class Solution { |
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 LuYaoQi's Blogs!