top1编程
← 返回题目
题解

爬行路线

1 条题解

  • 0
    @ 2026-8-5 23:59:33

    P4723 爬行路线(基础)

    解题思路

    第一步:看懂题目。 一只小蜜蜂在数字蜂房上爬,只能从标号小的蜂房爬到相邻且标号大的蜂房,问从 M 号蜂房爬到 N 号蜂房有多少种路线。

    第二步:找到关键规律。 蜂房是一个六边形拼成的图案,每个蜂房和它相邻的蜂房标号刚好差 1 和差 2。也就是说,站在标号为 k 的蜂房,下一步只能到 k+1 或 k+2 号蜂房。这就是这道题最关键的地方!

    第三步:把问题转化成熟悉的“上楼梯”问题。 知道了这个规律,问题就变成:从 1 开始,每次可以走 1 步或 2 步,问到达 N-M+1 有多少种走法。设 f[i] 表示从 1 到 i 的路线数,那么要到达 i,上一步只可能来自 i-1 或 i-2,所以 f[i] = f[i-1] + f[i-2]。这正好是斐波那契数列的递推式!f[1]=1,f[2]=1,之后每一项都等于前两项之和。

    第四步:为什么是从 1 到 N-M+1 而不是 M 到 N? 因为蜂房的规律每两个标号重复一次,从 M 到 N 的走法和从 1 到 N-M+1 的走法是一一对应的,路线数相同。比如样例从 1 到 14,N-M+1=14,f[14]=377,正好等于样例输出。

    第五步:再理解一下蜂房为什么这样编号。 第一行只有 1 号蜂房,第二行是 2、3 号,第三行是 4、5 号,第四行是 6、7 号……按照这种蛇形排列,每个蜂房向左下方和右下方伸出的两个蜂房,恰好就是它自己的编号加 1 和加 2。所以从任意一个蜂房出发,下一步只有两种选择,这正对应了斐波那契数列“要么跳 1 格、要么跳 2 格”的经典模型,就像上楼梯时一次可以跨一级或两级台阶一样。如果还是不放心,可以自己按规律画一画小蜂房,数一数从 1 到 5、从 1 到 6 的路线数,会发现确实分别是 5 和 8,正是斐波那契数列。

    第六步:注意边界与数据大小。 如果 M 和 N 只差 1,也就是两个相邻蜂房,那么只有直接爬过去这一种路线,此时 N-M+1=2,f[2]=1,结果正确。题目保证 M<N,且 N-M 最大是 90,最多需要算到 f[91]。斐波那契数列第 91 项大约是 4.6×10^18,用 long long(64 位整数)存储刚好放得下。

    参考代码

    // 蜜蜂爬行路线:从M爬到N,方案数等于斐波那契数列第(N-M+1)项
    #include <iostream>
    using namespace std;
    int main() {
        int from, to;
        cin >> from >> to;
        int target = to - from + 1; // 需要求斐波那契第 target 项
        long long fib[100];
        fib[1] = 1; fib[2] = 1;
        for (int i = 3; i <= target; i++)
            fib[i] = fib[i-1] + fib[i-2];
        cout << fib[target] << endl;
        return 0;
    }
    

    复杂度分析

    只需要从 3 递推到 target,target 最大是 91,所以时间复杂度是 O(N-M),最多 91 次加法,非常快。空间上用一个长度 100 的 long long 数组,空间复杂度也是 O(N-M) 量级,几乎可以忽略不计。

    • 1