优化 – 在F#/ Scala中优化相互递归的标准方法是什么?
发布时间:2020-12-16 09:02:04 所属栏目:安全 来源:网络整理
导读:这些语言不支持“原生”的相互递归函数优化,所以我猜它必须是蹦床或者……嘿……重写为循环)我想念一些东西吗? 更新:似乎我对FSharp撒了谎,但我只是没有看到谷歌搜索时相互尾调用的例子 解决方法 首先,F#本身支持相互递归的函数,因为它可以受益于.NET IL(
这些语言不支持“原生”的相互递归函数优化,所以我猜它必须是蹦床或者……嘿……重写为循环)我想念一些东西吗?
更新:似乎我对FSharp撒了谎,但我只是没有看到谷歌搜索时相互尾调用的例子 解决方法
首先,F#本身支持相互递归的函数,因为它可以受益于.NET IL(
MSDN)中提供的tailcall指令.但是,这有点棘手,可能不适用于.NET的某些替代实现(例如Compact Frameworks),因此您有时可能需要手动处理.
一般来说,我有几种方法可以解决它: > Trampoline – 当递归深度太高时抛出异常并实现处理异常的顶级循环(异常将携带信息以恢复调用).您也可以简单地返回一个值,指定应该再次调用该函数,而不是异常. 使用存储需要完成的工作的全局堆栈可以完成同样的事情.您可以向堆栈添加函数,而不是计划计时器.在顶层,程序将从堆栈中选择函数并运行它们. 为了给出第一种技术的具体例子,在F#中你可以这样写: type Result<′T> = | Done of ′T | Call of (unit -> ′T) let rec factorial acc n = if n = 0 then Done acc else Call(fun () -> factorial (acc * n) (n + 1)) 这也可以用于相互递归的函数.命令循环将简单地调用存储在Call(f)中的f函数,直到它产生Done并得到最终结果.我认为这可能是实现这一目标的最简洁方法. 我确信还有其他复杂的技术来处理这个问题,但那些是我所知道的(我用过的). (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
推荐文章
站长推荐
- angularjs:指令链接功能中的日志范围属性未定义
- scala – 如何在Play Framework的路由文件中使用
- shell杀死进程, adb server is out of date. kil
- 用于Vim的Python和Django插件
- scala中是否有等效的python reduce()函数?
- bash – scp和远程mkdir -p
- 图片: blueimp-Bootstrap-Image-Gallery-3.1.1-
- scala学习笔记——apply方法
- 前端每周清单:Webpack CLI 发布、Angular 5 可期
- webservice: Could not initialize Service NoSu
热点阅读