数的计算(递推)

题面(from luogu)
数的计算
我们要求找出具有下列性质数的个数(包含输入的自然数 n ):
先输入一个自然数 nn ( n \le 1000n≤1000 ),然后对此自然数按照如下方法进行处理:
①不作任何处理;
②在它的左边加上一个自然数,但该自然数不能超过原数的一半;
③加上数后,继续按此规则进行处理,直到不能再加自然数为止.

输入格式:
1 个自然数 n ( n≤1000 )
输出格式:
1 个整数,表示具有该性质数的个数。
样例.in
6
样例.out
6

题目分析
题目概述:略(解释的太清楚哩,一点包装都没有)
很多人在看到题目后会认为是一道模拟题,但是实际上,是可以用递推做地

我们先分析一下各种数据:
n=1 total=1 (1)
n=2 total=2 (2, 12)
n=3 total=2 (3, 13)
n=4 total=4 (4, 14, 124, 24)
n=5 total=4 (5, 15, 125, 25)
n=6 total=6 (6, 16, 126, 136, 26, 36)
n=7 total=6 (7, 17, 127, 137, 27, 37)
。。。。。。。
我们可以发现,在2与3,4与5,6与7上,出现了重复

如6:其中的模拟出的1,12,13,2,3是在其之前的数中出现过得,由此可以得到一个抽象的递推式子
f[6]=f[4] or f[5]+f[2] or f[3]+1;
但是由于 f[4]=f[5]; f[2]=f[3]; 所以:f[6]=f[5]+f[3]+1;
到这里,我们可以发现:3*2=6,5=6-1
所以: f[6]=f[6-1]+f[6/2]+1;
即:f[n]=f[n-1]+f[n/2]+1
但是由上,是出现了重复的,且是在偶数是更大的
所以可得一个具体的递推算法核心了:
f[i] = f[i-1];
if (i % 2 == 0) f[i]+=f[i / 2];
代码

#include <bits/stdc++.h>
using namespace std;

long n,f[10000];
int main()
{
    cin>>n; //输入

    f[1]=1; //初始化,譬如递归的边界
    for(int i = 2;i <= n ; i++)
    {
        f[i]=f[i-1]; //延续上一个的值
        if (i % 2 == 0) 
            f[i] += f[i / 2]; //如果是偶数,增加其值
    }

    cout<<f[n]; //输出
    return 0; //完美的结束程序
}
                                                     **蒟蒻新星c_uizrp_dzjopkl原创**
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值