我正在读这个问题:Decorator functions in Go,我想知道为什么在可接受的答案中示例的执行顺序对我来说似乎是颠倒的。
我将其分解为下面的最小示例,我想知道效果是不是由于函数链接造成的。
// Interesting Part
some_string := "Some_String"
var fn3 StringManipulator = ident
fn3 = AppendDecorator(" GOLANG", ToLower(PrependDecorator("DECORATED ", fn3)))
fmt.Println(fn3(some_string))
// Prints "DECORATED some_string golang"
// Function Definitions
func ToLower(m StringManipulator) StringManipulator {
    return func(s string) string {
        lower := strings.ToLower(s)
        return m(lower)
    }
}
func AppendDecorator(x string, m StringManipulator) StringManipulator {
        return func(s string) string {
            return m(s + x)
        }
}
func PrependDecorator(x string, m StringManipulator) StringManipulator {
    return func(s string) string {
        return m(x + s)
    }
}正如代码中提到的,这会产生“装饰的some_string golang”,表示函数是从左到右执行的,而普通函数的计算顺序是从最内到最外,即从右到左。这让我想起了转换矩阵的乘法后--这里的顺序也是“颠倒”的,比如M_1 * M_2 * M_3,这是因为函数链接还是什么原因?有人能帮我详细了解一下这是如何执行的吗?
提前谢谢你。
发布于 2019-02-08 12:45:22
我重写了你的例子来说明。
嵌套的函数调用从内到外执行。每次函数调用都会返回一个函数。最后,将AppendDecorator的结果赋给变量m,该结果本身是一个由所有装饰器组成的函数,如下所示:
m := func(s string) string {
    return ("DECORATED " + strings.ToLower(s + " GOLANG"))
}当我们执行m(s) (在fmt.Println(m(s)中)时,我们执行的是AppendDecorator返回的函数。此函数调用m(s + x),其中m是ToLower返回的函数。当此函数执行时,它调用m(lower),其中m是由PrependDecorator返回的函数。当此函数执行时,它调用m(x + s),其中m是我们传入的标识函数。
package main
import (
    "fmt"
    "strings"
)
// StringManipulator manipulate a string
type StringManipulator func(str string) string
// Identity a string manipulator that leaves the string unchanged
func Identity(s string) string {
    fmt.Println("Executing Identity manipulator")
    return s
}
// ToLower a lower case string manipulator
func ToLower(m StringManipulator) StringManipulator {
    fmt.Println("Returning ToLower manipulator")
    return func(s string) string {
        fmt.Println("Executing ToLower manipulator")
        lower := strings.ToLower(s)
        return m(lower)
    }
}
// AppendDecorator append a string manipulator
func AppendDecorator(x string, m StringManipulator) StringManipulator {
    fmt.Println("Returning Append manipulator")
    return func(s string) string {
        fmt.Println("Executing Append manipulator")
        return m(s + x)
    }
}
// PrependDecorator prepend a string manipulator
func PrependDecorator(x string, m StringManipulator) StringManipulator {
    fmt.Println("Returning Prepend manipulator")
    return func(s string) string {
        fmt.Println("Executing Prepend manipulator")
        return m(x + s)
    }
}
func main() {
    s := "Some_String"
    m := AppendDecorator(" GOLANG", ToLower(PrependDecorator("DECORATED ", Identity)))
    fmt.Println(m(s))
}m := AppendDecorator(" GOLANG", ToLower(PrependDecorator("DECORATED ", Identity)))的输出为:
Returning Prepend manipulator
Returning ToLower manipulator
Returning Append manipulatorfmt.Println(m(s))的输出是:
Executing Append manipulator
Executing ToLower manipulator
Executing Prepend manipulator
Executing Identity manipulator
DECORATED some_string golanghttps://stackoverflow.com/questions/54585917
复制相似问题