递归函数的内联优化,借助where子句(在Haskell中) 序曲 这篇文章说:

递归函数的内联优化,借助where子句(在Haskell中) 序曲 这篇文章说:,haskell,optimization,inline,ghc,Haskell,Optimization,Inline,Ghc,“对于自递归函数,环路断路器可以 只能是函数本身,因此内联pragma总是被忽略,”根据GHC手册 该答案描述了GHC通过内衬进行优化的方法 这篇(不相关的)文章解释了编译器无论如何都可以自由地拒绝显式内联建议。或者,将-O2标志传递给编译器可以获得与下面所示的优化版本相同的效果 示例代码 (如链接2所示) 问题 引用@amalloy的怀疑,当然 f仍然是“隐式传递的,与显式传递的一样多” 通过闭包创建程序在预优化版本]中传递f 机械“ 另一方面,我正在阅读fusion技术,这是链接1中描

“对于自递归函数,环路断路器可以 只能是函数本身,因此内联pragma总是被忽略,”根据GHC手册

  • 该答案描述了GHC通过内衬进行优化的方法

  • 这篇(不相关的)文章解释了编译器无论如何都可以自由地拒绝显式内联建议。或者,将
    -O2
    标志传递给编译器可以获得与下面所示的优化版本相同的效果

  • 示例代码 (如链接2所示)


    问题 引用@amalloy的怀疑,当然

    f
    仍然是“隐式传递的,与显式传递的一样多” 通过闭包创建程序在预优化版本]中传递f 机械“

    另一方面,我正在阅读fusion技术,这是链接1中描述的一种替代方法,尽管我并不试图寻找最快的实现来代替惯用风格

    只是好奇优化版本中的“where definition”技巧是否/如何工作(如果编译器决定内联这样的函数)


    额外的链接是最受欢迎的

    这是一个相当糟糕的例子,因为内联这段特定代码几乎没有什么好处。但在重要的情况下,类似的模式总是会减慢速度。最重要的是,在“优化的”
    func
    ,如果我写

    func myFun
    
    GHC可以内联
    func
    并获取

    let
      loop []  = []
      loop [x] = [x]
      loop (x:s:xs) = x : myFun s : loop xs 
    in loop
    

    在这种情况下,这并不意味着更好,但是如果严格要求
    myFun
    的结果,那么它会将对任意地址的调用替换为对已知地址的调用,这会更快。此外,如果
    myFun
    是在“有趣”的上下文中使用的(在该上下文中,对传递给它的参数或对其结果的处理是已知的),那么GHC可能会内联
    myFun
    ,以利用这一点。

    很吸引人,那么程序员是否必须传递明确的标志才能严格要求myFun?另外,请给出一些例子,说明内联可以真正产生重大影响,可能会扩展到GHC知道参数的情况下——可能不仅仅是它们的(具体)类型——第一个相当于
    \f->\list->case list of{…func…}
    ,而第二个相当于
    let{循环=清单-> {…循环…}的列表(在\f->循环)。GHC中的优化将将前者转换为后者。一般来说,这增加了共享(<代码> f<代码>),并提供了内联的机会;语用工作与C++的代码>内联< /代码>有很大的不同。
    
    let
      loop []  = []
      loop [x] = [x]
      loop (x:s:xs) = x : myFun s : loop xs 
    in loop