[英]Convert function to another type (function casting) in Go
我最近了解到,在net/http
程序包中,有一種用法使我最困惑。 這是函數類型轉換。 就像這樣:
(function a) ->convert to-> (type t)
(type t) ->implentments-> (interface i)
因此,如果有一個將接口i
作為參數的函數,它將調用函數a,這就是net/http
實現它的方式。
但是當我編寫自己的代碼時,我對這種模式有很多誤解。 我的代碼是這樣的:
package main
import (
"fmt"
)
type eat interface {
eat()
}
type aaa func()
func (op *aaa) eat() {//pointer receiver not right
fmt.Println("dog eat feels good")
}
///////////////////////////////////////////////
func dog() {
fmt.Println("I'm a dog")
}
///////////////////////////////////////////////
func feelsGood(a eat) {
a.eat()
}
func main() {
b := aaa(dog)
feelsGood(b)
}
//error:aaa does not implement eat (eat method has pointer receiver)
類型aaa具有方法eat,相同的函數名和參數簽名,符合接口eat的規則,但是為什么會出現該錯誤? 接收者重要嗎?
另一個問題是僅包含函數和類型,不包括接口,代碼如下所示:
package main
import (
"fmt"
)
type aaa func()
func (op *aaa) eat() {
op()
}
///////////////////////////////////////////////
func dog() {
fmt.Println("I'm a dog")
}
///////////////////////////////////////////////
func main() {
obj:=aaa(dog)
obj.eat()
}
//error:cannot call non-function op (type *aaa)
首先, op
具有匿名函數,而與錯誤無關?
其次,在刪除星號后它可以正常工作,但是為什么呢? op
是aaa
類型的實例,接收者是op
, op
代表函數dog()嗎? http包以相同的方式使用f(w,r)
,但有點難以理解。 op
是類型,實例還是匿名函數?
似乎我對函數轉換的理解不正確,但是我也檢查了Google上的許多帖子,沒有一個可以教我如何思考和正確使用它。謝謝!
問題1:
在Go中,對於類型T(例如您的aaa), T
和*T
具有不同的方法集。
因此,類型T的值只能訪問方法:
func(t T)Foo() { ... }
雖然* T類型的值可以訪問這兩種方法:
func(t T)Foo() { ... }
func(t *T)Bar() { ... }
就您而言,您有兩個選擇。 您可以聲明aaa
的eat
方法,而不是od *aaa
:
func (op aaa) eat() {
op()
}
或者,您將指針傳遞給b
來feelsGood
:
feelsGood(&b)
問題2:
是的,這個問題與第一個有關。 但是在這種情況下,您可以訪問該方法,因為obj.eat()
是(&obj).eat()
。
您的問題在於,無法在函數指針(op * aaa)上調用函數。 您的選擇是為aaa
而非*aaa
創建方法:
func (op aaa) eat() {
op()
}
或在值而不是指針上調用op
函數:
func (op *aaa) eat() {
(*op)()
}
對於您問題的第一部分:請參閱http://golang.org/doc/faq#different_method_sets ,該示例比我能更好地舉例說明了一切。 您甚至可以在stackoverflow和golang-nuts郵件列表中搜索該問題,因為它經常出現。
第二個是相同的恕我直言: aaa
沒有eat
方法(只有*aaa
擁有)。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.