如何解决此代码中的超时问题?

时间:2018-04-18 11:34:28

标签: algorithm timeout

我需要帮助。问题是在镜子中发光时找到对称的数字。 (例如0,1,11,101,1521(o)但1221和1010不是。) enter image description here 给出两个数字A和B,它们之间有空格。(输入) 范围是0 <= A,B <= 10 ^ 18。

输出是从A到B的打印对称数字计数。

ex)0 100(输入) 7(输出)

这是我在c ++中的代码,但由于数字范围很广,这些代码发生了超时。怎么解决这个问题?

int main()
{

    scanf("%d %d", &n,&m);

    for(int i=n;i<=m;i++)
    {
        char s[19];
        n=i;
        int len=0;

        do{ 
            s[len++]=n%10;
            n/=10; 
        } while(n>0);

        len--;
        int j = 0;

        for(j=0;j<=len/2;j++)
        {
            if(s[j]==s[len-j] && (s[j]==1 || s[j]==8 || s[j]==0))
                continue;

            if( (s[j]==2 && s[len-j]==5) || (s[j]==5 && s[len-j]==2))
                continue;

            break;
        }

        if(j>len/2)
            cnt++;
    }

    printf("%d\n",cnt);
    return 0;
}

1 个答案:

答案 0 :(得分:0)

您已经经历了一个非常痛苦的过程,看看哪些所有数字都是镜像。 Lukas Barth走在正确的轨道上,但速度甚至更快。你不需要构建数字;只计算有多少。

首先,你根本不关心这个数字的后半部分;通过施工,左半部分,右半部分是独一无二的。因此,您所要做的就是为每个数字长度计算左半部分。这将解决完全包含在范围内的10次幂的所有计数。

这使更多更容易。对于只有部分数字的范围(即A和/或B不是10的幂),您必须限制范围一端或另一端的前导数字。

您允许前导零。因此,每个数字有五种可能性:0,1,8,2,5。如果您有一个奇数位数,那么中间数字必须是它自己的镜像:0,1,8。

因此,让我们看一个例子,4位和5位数字。对于4位数字,您只需要前两个。每个数字都有5种可能性。这会产生5 * 5或25 four-digit mirror numbers

现在将其扩展为5位数字。您已经知道正好有25个两位数的开头。添加三个合法中间数字中的一个,即3 * 25或75 five-digit mirror numbers

将此扩展到完整的解决方案留给学生练习。