在Go中编写通用活页夹

在Go中编写通用活页夹,go,bind,argument-passing,Go,Bind,Argument Passing,考虑以下函数-第二个参数的绑定器 func bindSecond(value interface{}, f func(a interface{}, b interface{})) func (c interface{}) { return func(arg interface{}) { f(arg, value) } } 考虑一个函数 func f(x int, y int) {} 当试图将其用作活页夹中的参数时,go编译器会说: cannot use f (

考虑以下函数-第二个参数的绑定器

func bindSecond(value interface{}, f func(a interface{}, b interface{})) func (c interface{}) {
    return func(arg interface{}) {
        f(arg, value)
    }
}
考虑一个函数

func f(x int, y int) {}
当试图将其用作活页夹中的参数时,go编译器会说:

cannot use f (type func(int, int)) as type func(interface {}, interface {}) in argument to bindSecond.
你能给我建议一下在go golang中实现绑定器的正确方法吗?

用int替换接口{},它会工作的

或者,更重要的是,尝试使用Go提供的功能找到原始问题的解决方案,而不是试图从不同的范例中强制找到解决方案。

将接口{}替换为int,它就会起作用


或者,更重要的是,尝试使用Go提供的功能为您的原始问题找到解决方案,而不是试图从不同的范例中强制解决问题。

我知道您正在尝试做什么,一些模板,对吗?但这样做是行不通的。f funca接口{},b接口{}参数不是接口,因此它必须是匹配类型。您可以通过传递f接口{},然后使用reflect包对其进行操作来实现所需的功能

有些天真:


可行,但不是很漂亮。并且在运行时,如果发生任何意外情况,例如f不可调用,并且不接受两个参数,就会出现恐慌。或者您将错误的类型传递给inc.Complier将不再帮助您。

我知道您正在尝试做什么,一些模板,对吗?但这样做是行不通的。f funca接口{},b接口{}参数不是接口,因此它必须是匹配类型。您可以通过传递f接口{},然后使用reflect包对其进行操作来实现所需的功能

有些天真:


可行,但不是很漂亮。并且在运行时,如果发生任何意外情况,例如f不可调用,并且不接受两个参数,就会出现恐慌。或者您将错误的类型传递给inc.Complier将不再帮助您。

谢谢您的回答!当然,如果我用INT替换接口{},我的全部观点是,你不应该问如何在Go中制作活页夹,你应该问如何在Go中解决这个特定问题。这是一个更一般的问题,我如何使Go作为一种通用语言。答案是围棋不是通用语言。Go只有特定的类型。这不是疏忽;围棋队是故意这样设计的。你可以争论他们的选择是好是坏,但与之抗争只会产生可怕的结果。谢谢你的回答!当然,如果我用INT替换接口{},我的全部观点是,你不应该问如何在Go中制作活页夹,你应该问如何在Go中解决这个特定问题。这是一个更一般的问题,我如何使Go作为一种通用语言。答案是围棋不是通用语言。Go只有特定的类型。这不是疏忽;围棋队是故意这样设计的。你可以争论他们的选择是好是坏,但与之抗争只会产生可怕的结果。
package main

import (
    "fmt"
    "reflect"
)

func bindSecond(value interface{}, f interface{}) func(c interface{}) {
    return func(arg interface{}) {
        reflect.ValueOf(f).Call([]reflect.Value{reflect.ValueOf(arg), reflect.ValueOf(value)})
    }
}

func main() {
    sum := func(x int, y int) { fmt.Println(x + y) }
    inc := bindSecond(1, sum)
    inc(10)
}

// Prints 11