码迷,mamicode.com
首页 > 编程语言 > 详细

(算法)从0到n整数中数字2出现的次数

时间:2015-10-25 16:29:10      阅读:228      评论:0      收藏:0      [点我收藏+]

标签:

题目:

数出0到n(含)中数字2出现了几次。

思路:

1、暴力方法,数出每个数字包含几个2,然后累加起来。

2、分析:分别考虑数字n每一位出现2的次数,如123123;

从左往右考虑4123123;

考虑第一个1(即第6位),该位出现2的次数为4*10^6/10;

考虑第一个2(即第5位),该位出现2的次数为41*10^5/10+3123+1;

考虑第一个3(即第4位),该位出现2的次数为(412+1)*10^4/10;

附:除以10的原因在于:每10个数字,任意位出现2的概率为1/10.

总结规律:

第i位出现2个次数与该位所在的数字有关:

当第i位的数字小于2,出现次数就等于比其高位部分的数字*10^i/10,

当第i位的数字等于2,出现次数就等于比其高位部分的数字*10^i/10+n%(10^i),

当第i位的数字大于2,出现次数就等于(比其高位部分的数字+1)*10^i/10。

代码:

#include<iostream>
#include<sstream>
#include<math.h>
using namespace std;

template<class out_T,class in_T>
out_T convert(const in_T &t){
    stringstream ss;
    out_T result;
    ss<<t;
    ss>>result;
    return result;
}

int count2sInRangeAtDigit(int number,int d){
    int powerOf10=pow(10,d);
    int nextPowerOf10=powerOf10*10;
    int right=number%powerOf10;

    int roundDown=number-number%nextPowerOf10;
    int roundUp=roundDown+nextPowerOf10;

    int digit=(number/powerOf10)%10;
    if(digit<2)
        return roundDown/10;
    else if(digit==2)
        return roundDown/10+right+1;
    else
        return roundUp/10;
}

int count2sInRange(int number){
    int count=0;
    string str;
    str=convert<string>(number);
    int len=str.size();

    for(int digit=0;digit<len;digit++)
        count+=count2sInRangeAtDigit(number,digit);
    return count;
}

int main(){
    int n;
    while(cin>>n){
        cout<<count2sInRange(n)<<endl;
    }
    return 0;
}

 

(算法)从0到n整数中数字2出现的次数

标签:

原文地址:http://www.cnblogs.com/AndyJee/p/4908899.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!