Golang學習筆記之方法(method)
法總是繫結物件例項,並隱式將例項作為第⼀實參 (receiver)。
• 只能為當前包內命名型別定義⽅法。
• 引數 receiver 可任意命名。如⽅法中未曾使⽤,可省略引數名。
• 引數 receiver 型別可以是 T 或 *T。基型別 T 不能是接⼝或指標。
• 不⽀持⽅法過載, receiver 只是引數簽名的組成部分。
• 可⽤例項 value 或 pointer 調⽤全部⽅法,編譯器⾃動轉換。
• Go 不允許同名函式,但是同名方法可以定義在不同的型別上
• method和receiver必須在同一個包裡定義
• 作為函式引數,值型別就是值型別,指標型別就是指標型別
• 方法有一個值型別和指標型別的接受者時,都可以直接呼叫,內部會
自動進行語法的轉換。
一個方法只是一個函式,它有一個特殊的接收者(receiver)型別,該接收者放在 func 關鍵字和函式名之間。接收者可以是結構體型別或非結構體型別。可以在方法內部訪問接收者。
一般語法為:
func (t receiver_type) methodName(parameter list) {}
一、引數 receiver 型別可以是 T 或 *T。以指標為接收者也是可以的。
兩者的區別在於, 以*T為接收者時,方法內部對其的修改對於外部有效,而以 T作為接受者時,對於外部無效。
1func (e Employee) changeName(newName string) {
2 e.name = newName
3}
4func (e *Employee) changeAge(newAge int) {
5 e.age = newAge
6}
7 emp1 := Employee{
8 name: "張三",
9 salary: 6000,
10 currency: "$",
11 age: 18,
12 Address: Address{"山東", "濟南"},
13 }
14 emp1.displaySalary()
15
16 fmt.Println("Before call changeName ", emp1.name)
17 //修改名字,未發生變化因為是值傳遞
18 emp1.changeName("zhangsan")
19 fmt.Println("After call changeName ", emp1.name) //After call changeName 張三
20
21 fmt.Println("Before change age", emp1.age)
22 //利用指標來修改年齡
23 emp1.changeAge(50)
24 fmt.Println("After change age", emp1.age) //After change age 50
二、Go 不允許同名函式,但是同名方法可以定義在不同的型別上
1//Rectangle 程式碼規範
2type Rectangle struct {
3 width float32
4 height float32
5}
6//Circle 程式碼規範
7type Circle struct {
8 radius float32
9}
10func (e Employee) changeName(newName string) {
11 e.name = newName
12}
13func (e *Employee) changeAge(newAge int) {
14 e.age = newAge
15}
16func main() {
17 //計算面積
18 re := Rectangle{20, 30}
19 c := Circle{40}
20 //兩個型別呼叫同名方法
21 fmt.Println(re.getArea())
22 fmt.Println(c.getArea())
23}
1emp1 := Employee{
2 name: "張三",
3 salary: 6000,
4 currency: "$",
5 age: 18,
6 Address: Address{"山東", "濟南"},
7 }
8 //提階
9 emp1.fullAddress() //山東 濟南,提階相當於直接訪問Address裡的
10 emp1.Address.fullAddress() //山東 濟南
四、非結構型別的方法
非結構體型別也可以定義方法,不過這裡需要注意一點。為了定義某個型別的方法,接收者型別的定義與方法的定義必須在同一個包中。
因為必須在一個包中而int則在main包中我們沒法去定義這個裡為了簡單直觀,給int宣告瞭別名
1//非結構體方法擴充套件
2type myInt int
3
4func (a myInt) add(b myInt) myInt {
5 return a + b
6}
7func main() {
8 //呼叫擴充套件的方法
9 num1 := myInt(5)
10 num2 := myInt(10)
11 sum := num1.add(num2)
12 fmt.Println("Sum is", sum)
13
14}
下面附上完整例項程式
1package main
2
3import (
4 "fmt"
5 "math"
6)
7
8//Employee 需要新增註釋或者改成非匯出變數(首字母小寫)
9type Employee struct {
10 name string
11 currency string
12 salary int
13 age int
14 Address
15}
16
17//Address 程式碼規範
18type Address struct {
19 city string
20 state string
21}
22
23//Rectangle 程式碼規範
24type Rectangle struct {
25 width float32
26 height float32
27}
28
29//Circle 程式碼規範
30type Circle struct {
31 radius float32
32}
33
34//Employee 的方法
35func (e Employee) displaySalary() {
36 fmt.Println(e)
37}
38func (e Employee) changeName(newName string) {
39 e.name = newName
40}
41func (e *Employee) changeAge(newAge int) {
42 e.age = newAge
43}
44
45//Address 的方法
46func (add Address) fullAddress() {
47 fmt.Println(add.city, add.state)
48}
49
50//Rectangle 的方法計算面積
51func (r Rectangle) getArea() float32 {
52 return r.width * r.height
53}
54
55//Circle 的方法
56func (c Circle) getArea() float32 {
57 return math.Pi * c.radius * c.radius
58}
59
60//非結構體方法擴充套件
61type myInt int
62
63func (a myInt) add(b myInt) myInt {
64 return a + b
65}
66func main() {
67 //呼叫方法
68 emp1 := Employee{
69 name: "張三",
70 salary: 6000,
71 currency: "$",
72 age: 18,
73 Address: Address{"山東", "濟南"},
74 }
75 emp1.displaySalary()
76
77 fmt.Println("Before call changeName ", emp1.name)
78 //修改名字,未發生變化因為是值傳遞
79 emp1.changeName("zhangsan")
80 fmt.Println("After call changeName ", emp1.name) //After call changeName 張三
81
82 fmt.Println("Before change age", emp1.age)
83 //利用指標來修改年齡
84 emp1.changeAge(50)
85 fmt.Println("After change age", emp1.age) //After change age 50
86
87 //提階
88 emp1.fullAddress() //山東 濟南,提階相當於直接訪問Address裡的
89 emp1.Address.fullAddress() //山東 濟南
90
91 //計算面積
92 re := Rectangle{20, 30}
93 c := Circle{40}
94 //兩個型別呼叫同名方法
95 fmt.Println(re.getArea())
96 fmt.Println(c.getArea())
97
98 //呼叫擴充套件的方法
99 num1 := myInt(5)
100 num2 := myInt(10)
101 sum := num1.add(num2)
102 fmt.Println("Sum is", sum)
103
104}
原文釋出時間為:2018-12-12
本文作者:Golang語言社群
本文來自雲棲社群合作伙伴“ Golang語言社群”,瞭解相關資訊可以關注“Golangweb”微信公眾號
相關文章
- golang 學習筆記Golang筆記
- goLang學習筆記(一)Golang筆記
- goLang學習筆記(二)Golang筆記
- goLang學習筆記(三)Golang筆記
- goLang學習筆記(四)Golang筆記
- 【學習筆記】Golang 切片筆記Golang
- GOLang 學習筆記(一)Golang筆記
- golang 學習筆記1Golang筆記
- Python學習筆記|Python之特殊方法Python筆記
- Golang學習筆記-1.6 函式Golang筆記函式
- Golang學習筆記(1):包管理Golang筆記
- Go語言學習筆記(七)之方法Go筆記
- golang學習筆記(二)—— 深入golang中的協程Golang筆記
- Golang學習筆記-IDE安裝指南Golang筆記IDE
- Golang學習筆記(一):命名規範Golang筆記
- 《Golang學習筆記》error最佳實踐Golang筆記Error
- golang學習筆記(1):安裝&helloworldGolang筆記
- GO 方法學習筆記Go筆記
- Golang 學習筆記八 錯誤異常Golang筆記
- Golang學習筆記(十九):Channel初步接觸Golang筆記
- Golang 學習筆記——tun/tap 程式設計Golang筆記程式設計
- 統計學習方法筆記-感知機學習方法筆記
- 學習筆記——物件方法整理筆記物件
- 統計學習方法筆記筆記
- 學習筆記之測試筆記
- JS學習筆記之this指向JS筆記
- flask學習筆記之blueprintFlask筆記
- Swoft 學習筆記之配置筆記
- 學習筆記:DOM之appendChild筆記APP
- node學習筆記之39筆記
- Web之http學習筆記WebHTTP筆記
- Netty學習筆記之ChannelHandlerNetty筆記
- Pytorch學習筆記之tensorboardPyTorch筆記ORB
- Boltdb學習筆記之〇--概述筆記
- 初學Golang的筆記Golang筆記
- 尹成學院golang學習快速筆記(2)表示式Golang筆記
- 尹成學院golang學習快速筆記(1)型別Golang筆記型別
- 我的 golang 學習筆記系列二:golang的函式運用Golang筆記函式