3G.处女座和小姐姐(三)(C++)

处女座和小姐姐(三)(C++)

点击做题网站链接

题目描述
经过了选号和漫长的等待,处女座终于拿到了给小姐姐定制的手环,小姐姐看到以后直呼666!
处女座其实也挺喜欢6这个数字的,实际上他做手环的时候选取的k=6。所以他对于包含数码6的数字极其敏感。每次看到像4567这样的数字的时候他的心就像触电了一样,想起了小姐姐。
现在你要给处女座展示一系列数字,你想知道他的内心会激动多少次。对于同一个数字,他最多只会激动一次,即如果这个数是66666,他还是只会激动一次。

输入描述:
一行包括两个数字l,r,表示你给处女座展示的数字范围为[l,r]。

输出描述:
一行一个整数,表示处女座内心激动的次数。

示例1
输入

10 20

输出
1

备注:
0lr10180≤l≤r≤10^{18}

解题思路:
本题要求一个区间内含有6的数字的个数。
将solve[l,r]转换为solve[0,r]-solve[0,l-1]
时间复杂度:𝑂(𝑙𝑒𝑛),其中len代表数的位数。

解题代码:

#include<iostream>
using namespace std;
long long int l,r;

bool check(long long int x)//判断x的每一位是否为6
{
    while(x)
    {
        if( x%10==6 )
            return true;
        x /= 10;
    }
    return false;
}

long long int solve(long long int x)
{
    if(x<=0) return 0;//如果x是负数
    long long int i;
    int Count = 0;
    for(i=x/10*10;i<=x;++i)//每10个数为一组
        if( check(i) ) Count++;//如果i的任意一位上有数字6,则Count++
    return 9*solve(x/10-1) + Count + x/10;//x/10指每10个数肯定有一个6,Count是指目前的十位数里有几个包含6的数字
    //solve的递归思想是每次都检查2位数中的6的个数,最后越分越小
}

int main()
{
    cin >> l >> r;
    cout << solve(r)-solve(l-1);
}

超时代码:

#include <iostream>
using namespace std;
int main()
{
    long long int l,r,temp,Count=0;
    cin >> l >> r;
    for(int i=l;i<=r;++i)//活该超时
    {
        temp = i;
        while(temp)
        {
            if( temp%10==6 )
            {
                Count++;
                break;
            }
            temp /= 10;
        }
    }
    cout << Count << endl;
}
posted @ 2019-01-26 21:32  Sherry_Yue  阅读(202)  评论(0编辑  收藏  举报