您好,登錄后才能下訂單哦!
這篇文章將為大家詳細講解有關Go中如何聲明方法,小編覺得挺實用的,因此分享給大家做個參考,希望大家閱讀完這篇文章后可以有所收獲。
Go支持一些面向?qū)ο缶幊烫匦?,方法是這些所支持的特性之一。
在Go中,我們可以為類型T
和*T
顯式地聲明一個方法,其中類型T
必須滿足四個條件:
T
必須是一個定義類型;
T
必須和此方法聲明定義在同一個代碼包中;
T
不能是一個指針類型;
T
不能是一個接口類型。
類型T
和*T
稱為它們各自的方法的屬主類型(receiver type)。 類型T
被稱作為類型T
和*T
聲明的所有方法的屬主基類型(receiver base type)
如果我們?yōu)槟硞€類型聲明了一個方法,以后我們可以說此類型擁有此方法,一個方法聲明和一個函數(shù)聲明很相似,但是比函數(shù)聲明多了一個額外的參數(shù)聲明部分。 此額外的參數(shù)聲明部分只能含有一個類型為此方法的屬主類型的參數(shù),此參數(shù)稱為此方法聲明的屬主參數(shù)(receiver parameter)。 此屬主參數(shù)聲明必須包裹在一對小括號()之中。 此屬主參數(shù)聲明部分必須處于func關鍵字和方法名之間
下面是一個方法聲明的例子:
// Age和int是兩個不同的類型。我們不能為int和*int // 類型聲明方法,但是可以為Age和*Age類型聲明方法。 type Age int func (age Age) LargerThan(a Age) bool { return age > a } func (age *Age) Increase() { *age++ } // 為自定義的函數(shù)類型FilterFunc聲明方法。 type FilterFunc func(in int) bool func (ff FilterFunc) Filte(in int) bool { return ff(in) } // 為自定義的映射類型StringSet聲明方法。 type StringSet map[string]struct{} func (ss StringSet) Has(key string) bool { _, present := ss[key] return present } func (ss StringSet) Add(key string) { ss[key] = struct{}{} } func (ss StringSet) Remove(key string) { delete(ss, key) } // 為自定義的結(jié)構體類型Book和它的指針類型*Book聲明方法。 type Book struct { pages int } func (b Book) Pages() int { return b.pages } func (b *Book) SetPages(pages int) { b.pages = pages }
對每個方法聲明,編譯器將自動隱式聲明一個相對應的函數(shù)。 比如對于上一節(jié)的例子中為類型Book
和*Book
聲明的兩個方法,編譯器將自動聲明下面的兩個函數(shù):
func Book.Pages(b Book) int { return b.pages // 此函數(shù)體和Book類型的Pages方法體一樣 } func (*Book).SetPages(b *Book, pages int) { b.pages = pages // 此函數(shù)體和*Book類型的SetPages方法體一樣 }
在上面的兩個隱式函數(shù)聲明中,它們各自對應的方法聲明的屬主參數(shù)聲明被插入到了普通參數(shù)聲明的第一位。 它們的函數(shù)體和各自對應的顯式方法的方法體是一樣的。
兩個隱式函數(shù)名Book.Pages
和(*Book).SetPages
都是aType.MethodName
這種形式的。 我們不能顯式聲明名稱為這種形式的函數(shù),因為這種形式不屬于合法標識符。這樣的函數(shù)只能由編譯器隱式聲明。 但是我們可以在代碼中調(diào)用這些隱式聲明的函數(shù)
一個方法原型可以看作是一個不帶func關鍵字的函數(shù)原型。 我們可以把每個方法聲明看作是由一個func關鍵字、一個屬主參數(shù)聲明部分、一個方法原型和一個方法體組成
方法事實上是特殊的函數(shù)。方法也常被稱為成員函數(shù)。 當一個類型擁有一個方法,則此類型的每個值將擁有一個不可修改的函數(shù)類型的成員(類似于結(jié)構體的字段)。 此成員的名稱為此方法名,它的類型和此方法的聲明中不包括屬主部分的函數(shù)聲明的類型一致。 一個值的成員函數(shù)也可以稱為此值的方法。
一個方法調(diào)用其實是調(diào)用了一個值的成員函數(shù)。假設一個值v
有一個名為m
的方法,則此方法可以用選擇器語法形式v.m
來表示。
下面這個例子展示了如何調(diào)用為Book
和*Book
類型聲明的方法:
package main import "fmt" type Book struct { pages int } func (b Book) Pages() int { return b.pages } func (b *Book) SetPages(pages int) { b.pages = pages } func main() { var book Book fmt.Printf("%T \n", book.Pages) // func() int fmt.Printf("%T \n", (&book).SetPages) // func(int) // &book值有一個隱式方法Pages。 fmt.Printf("%T \n", (&book).Pages) // func() int // 調(diào)用這三個方法。 (&book).SetPages(123) book.SetPages(123) // 等價于上一行 fmt.Println(book.Pages()) // 123 fmt.Println((&book).Pages()) // 123 }
和普通參數(shù)傳參一樣,屬主參數(shù)的傳參也是一個值復制過程。 所以,在方法體內(nèi)對屬主參數(shù)的直接部分的修改將不會反映到方法體外
關于“Go中如何聲明方法”這篇文章就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,使各位可以學到更多知識,如果覺得文章不錯,請把它分享出去讓更多的人看到。
免責聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權內(nèi)容。