递归视角下

def listSum(numbers):
    if not numbers:
        return 0
    else:
        (f, rest) = numbers
    return f + listSum(rest)

myList = (1, (2, (3, (4,None))))
total = listSum(myList)
print(total)

while循环何时退出? 恐怕是while循环技巧所在,即选择恰当的变量作为退出循环的条件判断。

下面的栗子选择了哪个变量作为退出条件?

原题来自宁波第23届中小学信息比赛小学组决赛最后一道题。尝试用python代替原题要求的pascal count.pas/exe)

alt

问题描述: 小Q的编程技术在一次搭积木比赛中也成了秘密武器。原来,比赛的规则是这样的:给你N个小木块(全部为一样大小的正方体)。快速搭成如下图规则的形状(下图为5层的规模),要求层数为最大限度。

由于小Q编了个程序,只要输入小木块的个数N,就可以马上求出最多可以搭几层,还剩几个,所以小Q每次都是一次成功,从不需要翻工,速度也就领先了,你会编小Q这样的程序吗?

【输入数据】

输入文件count.in:文件中只有一个整数N,表示小木块的个数,已知1≤N≤2^31。

【输出数据】

输出文件count.out:文件中有两行整数,第一行是最多可以堆的层数,第二行是剩余的小木块

Python语言的搭积木的诀窍 解法仅供参考

图片

递归的妙处:

第一条:每次递归都能将问题规模缩减下来。

第二条:对应递归终止条件,递归必须有个出口,不然会陷入无限递归当中。

第三条:将递归问题细分为更小的递归问题,然后再进行递归调用。

首先,只需要找到相邻两层之间数量关系,较大层数和小木块数量之间的关系表达为为consumer()函数

请看图:第1层是1,第2层是3,第3层用掉的木块是x,那么前3层用掉的木块总数是前2层用掉的总数,再加上第3层的木块数量。

留意:前3层和第3层所指不同,显然前3层包含第3层。持续倒推,就可以建立起第n层和第1层之间的数量关系。

alt

第n-1层需要多少个小木块作为输入参数,

x = consumer(n-1)

推出第n层需要多少小木块,

consumer(n)=consumer(n-1) + 0.5*(n**2+n)

为啥是第2层开始,总能表达为

consumer(n-1) + 0.5*(n**2+n)

为何1-> n 层的cube总的数量 = 第 n-1 层数量 + 0.5*(n**2+n)

符合以上数学关系的理由是第 n 层木块数量与 n 存在关系,不妨从求解三角形的面积公式得到灵感:

1+2+3+....n = 0.5*(n**2+n)

alt

第n层的平面图计算高斯数

please enter the cube numeber:20
4, 0

please enter the cube numeber:100
7, 16.0

please enter the cube numeber:1000
17, 31.0

但python递归的问题爆栈在随手将 n 大到离谱时如约而至!呵呵

please enter the cube numeber:10000000000000

...
RecursionError: maximum recursion depth exceeded in comparison

那么,这时候有两个办法:

1、设法取消递归栈的上限:996 次; 2、或者改用循环的递推实现;

如何理解递归和循环?

SOLID原则:

分离出子函数layerSum(n)计算第 n 层有多少cube;

主函数 consumeWhile(total)判断累积cube超过total为退出循环的条件判断;

*可以与递归写法的结果比较是否一致

# SOLID分离原则 
def layersSum(n):
    # 第 n 层有多少cube
    return 0.5 *(n**2 + n)

上述可以灵活修改每一层的几何形状,如改为正方形等等;

def consumeWhile(total):
    # 表达相邻两层之间的数量关系
    # cur,upper = layers(1),layers(2)
    # upper变量是从 1-n 层共有多少cube
    cur,layer = 0,0
    while cur <= total:
        cur += layersSum(layer)
        if cur == total:
            return layer,0
        elif cur > total:
            return layer-1,total - (cur-layersSum(layer))
        layer += 1
        
        
total = 100000000
print(consumeWhile(total))

(842, 153956.0)

递归的写法优雅而有趣,但实际项目工程中并不是首选。正如在while循环中看到当 total 数字很大时,递归的不仅运算花费的时间多且易溢出而报错。

这时循环的写法系统的开销更少。

本文由 mdnice 多平台发布

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/136045.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Linux学习之Redis集群部署

Redis集群部署 准备集群环境 创建集群 # 准备集群环境--配置192.168.88.51(host51) [rootlocalhost ~]# yum install -y redis [roothost51 ~]# vim /etc/redis.conf bind 192.168.88.51 cluster-enabled yes cluster-config-file nodes-6379.conf cluster-node-timeout 5000…

malloc是如何实现内存分配的?

文章目录 前言一、malloc实现原理概括&#xff1f;二、brk() 函数与mmap()函数三、mmap实现原理普通读写与mmap对比mmap内存映射实现过程mmap 的适用场景 前言 在C和C中&#xff0c;malloc函数是用于动态分配内存的常用函数。本文将深入探究malloc函数的内存分配实现机制&…

【Vue入门】语法 —— 插值、指令、过滤器、计算属性、监听器

目录 一、模版语法 1.1 插值 1.1.1 文本 1.1.2 html解析 1.1.3 属性 1.1.4 表达式 1.2 指令 1.2.1 核心指令 1.2.3 动态参数 二、过滤器 2.1 局部过滤器 2.2 全局过滤器 三、计算属性 四、监听器 五、排座案例 小结&#xff1a;计算属性和监听属性的区别 一、模…

怎么防止360安全卫士修改默认浏览器?

默认的浏览器 原先选项是360极速浏览器&#xff08;如果有安装的话&#xff09;&#xff0c;我这里改成了Chrome。 先解锁 才能修改。

今年嵌入式行情怎么样?

今年嵌入式行情怎么样&#xff1f; 嵌入式技术今年可以说是IT领域中最炙手可热的之一。随着中年危机和内卷问题的出现&#xff0c;越来越多的互联网从业者将目光投向了嵌入式领域。国内的嵌入式市场一直受终端需求变化的影响而波动&#xff0c;但随着国内产业自主化的发展趋势…

uniapp 小程序 父组件调用子组件方法

答案&#xff1a;配合小程序API > this.selectComponent("")&#xff0c;来选择组件&#xff0c;再使用$vm选择组件实例&#xff0c;再调用方法&#xff0c;或者data 1 设置组件的id,如果你的多端&#xff0c;请跟据情况设置ref,class,id&#xff0c;以便通过小…

9.18号作业

完善登录框 点击登录按钮后&#xff0c;判断账号&#xff08;admin&#xff09;和密码&#xff08;123456&#xff09;是否一致&#xff0c;如果匹配失败&#xff0c;则弹出错误对话框&#xff0c;文本内容“账号密码不匹配&#xff0c;是否重新登录”&#xff0c;给定两个按钮…

如何将 JavaScript Excel XLSX 查看器添加到Web应用程序

在 JavaScript 中创建 Excel 查看器可能是一项艰巨的任务&#xff0c;但使用 SpreadJS JavaScript 电子表格&#xff0c;创建过程要简单得多。在本教程博客中&#xff0c;我们将向您展示如何使用 SpreadJS 的强大功能来创建一个查看器&#xff0c;该查看器允许您在 Web 浏览器中…

with ldid... /opt/MonkeyDev/bin/md: line 326: ldid: command not found

吐槽傻逼xcode 根据提示 执行了这个脚本/opt/MonkeyDev/bin/md 往这里面添加你brew install 安装文件的目录即可

【实验】H3C校园双出口配置案例,可跟做!

【微|信|公|众|号&#xff1a;厦门微思网络】 1.案例拓补 该拓扑图中的校园网内部分为两个网段&#xff1a;一个为学生校舍网段&#xff08;192.168.2.0&#xff09;&#xff0c;主要访问电信提供的internet服务器&#xff1b;另外一个网段为校园办公和教学用网段&#xff08;…

操作系统的体系结构

一、内核结构 操作系统内核也有两种类别&#xff1a;大内核结构、微内核结构 大内核结构&#xff1a;也叫宏内核/单内核。将操作系统的主要功能模块都作为操作系统内核。大内核结构包括进程管理、存储器管理、设备管理等功能&#xff08;第四层&#xff09;和时钟管理、中断处理…

爬虫工作者必备:使用爬虫ip轻松获得最强辅助

在进行网络数据爬取时&#xff0c;爬虫ip成为了爬虫工作者们的得力辅助。通过使用爬虫ip&#xff0c;可以实现IP地址的伪装和分布式请求&#xff0c;有效规避访问限制和提高爬取效率。本文将为爬虫工作者们分享关于使用爬虫ip的知识&#xff0c;帮助您轻松获取最强辅助&#xf…

【SpringMVC】基于 Spring 的 Web 层MVC 框架

&#x1f384;欢迎来到边境矢梦的csdn博文&#x1f384; &#x1f384;本文主要梳理SpringMVC : 基于 Spring 的 Web 层MVC 框架 &#x1f384; &#x1f308;我是边境矢梦&#xff0c;一个正在为秋招和算法竞赛做准备的学生&#x1f308; &#x1f386;喜欢的朋友可以关注一下…

VMware workstation 中centos7虚拟机在nat模式下怎么配置网卡,指定我想要的IP并且可以联网

1、首先打开我们的虚拟网络编辑器 2、查看我们的网关 3、查看IP池&#xff0c;根据需求自己设置 4、打开centos7虚拟机 编辑网卡配置 vim /etc/sysconfig/network-scripts/ifcfg-ens160####我的网卡是ens160TYPEEthernet PROXY_METHODnone BROWSER_ONLYno BOOTPROTOstatic …

「聊设计模式」之原型模式(Prototype)

&#x1f3c6;本文收录于《聊设计模式》专栏&#xff0c;专门攻坚指数级提升&#xff0c;助你一臂之力&#xff0c;带你早日登顶&#x1f680;&#xff0c;欢迎持续关注&&收藏&&订阅&#xff01; 前言 设计模式是软件开发中经过长期实践总结的经验和规范&#…

git 查看当前版本号

你看&#xff0c;那个人好像一条狗哎。 ——周星驰 《大话西游》 要查看当前 Git 仓库的版本号&#xff0c;您可以使用以下命令&#xff1a; git log --oneline -n 1 这会显示最近一次的提交信息&#xff0c;包括提交的哈希值&#xff08;版本号&#xff09;和提交的摘要信息…

微服务保护-流量控制

流量控制 雪崩问题虽然有四种方案&#xff0c;但是限流是避免服务因突发的流量而发生故障&#xff0c;是对微服务雪崩问题的预防。我们先学习这种模式 簇点链路 当请求进入微服务时&#xff0c;首先会访问DispatcherServlet&#xff0c;然后进入Controller、Service、Mapper&…

vue基础知识十三:Vue中的$nextTick有什么作用?

一、NextTick是什么 官方对其的定义 在下次 DOM 更新循环结束之后执行延迟回调。在修改数据之后立即使用这个方法&#xff0c;获取更新后的 DOM 什么意思呢&#xff1f; 我们可以理解成&#xff0c;Vue 在更新 DOM 时是异步执行的。当数据发生变化&#xff0c;Vue将开启一个异…

神经网络 01(介绍)

一、神经网络 人工神经网络 (Artificial Neural Network&#xff0c;简写为ANN)也简称为神经网络 (NN)&#xff0c;是一种模仿生物神经网络结构和功能的 计算模型。人脑可以看做是一个生物神经网络&#xff0c;由众多的神经元连接而成。各个神经元传递复杂的电信号&#xff0c…

HTTP代理与VPN:网络代理技术的比较

HTTP代理和VPN是两种常见的网络代理技术&#xff0c;它们可以帮助用户隐藏自己的IP地址、保护网络隐私、绕过网络限制等。本文将介绍HTTP代理和VPN的定义、工作原理、优缺点以及使用场景。 一、HTTP代理 HTTP代理是一种通过代理服务器转发网络请求的技术。当用户发起网络请求时…