package main // 聲明main包
import( // 導入包
"fmt"
)
func main(){ // 聲明main主函數
fmt.Println("hello worod") // 打印輸出
}
func 函數名(形式參數列表)(返回值列表){
函數體
}
// 形式參數包括形式參數名以及參數類型
// 返回值列表描述了返回值的變量名以及類型
var a, b *int // 聲明,此處a,b即為指針
var(
a int
b string
c []float32
)
/*
Go語言的基本類型有:
bool
string
int、int8、int16、int32、int64
uint、uint8、uint16、uint32、uint64、uintptr
byte // uint8 的別名
rune // int32 的別名 代表一個 Unicode 碼
float32、float64
complex64、complex128
當一個變量被聲明之後,系統自動賦予他該類型的零值:
int 0
float 0.0
bool false
string ""
指針 nil
*/
var 變量名 類型 = 表達式 // 變量初始化標準格式
var 變量名 = 表達式 // 編譯器推導類型的格式
變量名 := 表達式 // 短變量聲明並初始化
i,j := 1, 2 // 簡短變量聲明語句,定義變量同時顯示初始化
i, j = j, i // 多重賦值,交換
// 匿名變量:下劃線“_”在go中稱為空白標識符
/* 二、變量的作用域 */
/*
全局變量,函數體外,聲明全局變量必須用var關鍵字聲明,私有變量首字母小寫,公有變量首字母大寫
局部變量,函數體內
形式參數,形參,函數名變量後括號中的變量
*/
/* 三、數據類型轉換 */
a := 5.0
b := int(a)
/* 四、指針 pointer */
/*
每個變量都擁有地址,指針的值就是地址
要明白指針,需要知道幾個概念:指針地址、指針類型和指針取值
v 代表被取地址的變量,變量 v 的地址使用變量 ptr 進行接收,
ptr 的類型為*T,稱做 T 的指針類型,*代表指針
*/
func main() {
// 準備一個字符串類型
var house = "Malibu Point 10880, 90265"
// 對字符串取地址, ptr類型為*string,稱為指針
ptr := &house
// 打印ptr的類型
fmt.Printf("ptr type: %T\\n", ptr) // T型數據 ptr type: *string
// 打印ptr的指針地址
fmt.Printf("address: %p\\n", ptr) // address: 0xc0420401b0
// 對指針進行取值操作
value := *ptr
// 取值後的類型
fmt.Printf("value type: %T\\n", value) // value type: string
// 指針取值後就是指向變量的值
fmt.Printf("value: %s\\n", value) //value: Malibu Point 10880, 90265
}
/*
1、對變量進行取地址操作使用&操作符,可以獲得這個變量的指針變量
2、指針變量的值是指針地址
3、對指針變量進行取值操作使用*操作符,可以獲得指針變量只想的原始變量的值
*/
// 使用指針修改值,交換函數
func swap(a, b *int) {
// 取a指針的值, 賦給臨時變量t
t := *a
// 取b指針的值, 賦給a指針指向的變量
*a = *b
// 將a指針的值賦給b指針指向的變量
*b = t
}
func main() {
// 準備兩個變量, 賦值1和2
x, y := 1, 2
// 交換變量值
swap(&x, &y)
// 輸出變量值
fmt.Println(x, y) // 2 1
}
// 創建指針的另一種方法——new() 函數
str := new(string)
*str = "Go語言教程"
fmt.Println(*str)
// new() 函數可以創建一個對應類型的指針,創建過程會分配內存,被創建的指針指向默認值。
/* --> 五、變量逃逸分析*/
/*
1、棧:線性表數據結構,棧只允許從線性表的同一端放入和取出數據,按照新進先出的順序
*/
func calc(a, b int) int {
var c int
c = a * b
var x int
x = c * 10
return x
}
/*
上面代碼會進行變量 c 和 x 的分配過程。Go語言默認情況下會將 c 和 x 分配在棧上,這兩個變量在 calc()
函數退出時就不再使用,函數結束時,保存 c 和 x 的棧內存再出棧釋放內存,
整個分配內存的過程通過棧的分配和回收都會非常迅速
*/
/*
變量逃逸--自動決定變量分配方式,提高運行效率
Go語言將這個過程整合到了編譯器中,命名為“變量逃逸分析”。
通過編譯器分析代碼的特徵和代碼的生命週期,決定應該使用堆還是棧來進行內存分配。
編譯器覺得變量應該分配在堆和棧上的原則是:
變量是否被取地址
變量是否發生逃逸
*/
/* --> 六、常量,*/
const name [type] = value // 常量聲明語句格式
const b string = "abd" // 顯式類型定義
const b = "abc" // 隱式類型定義
const (
a = 1
b
c = 2
d
)
fmt.Println(a, b, c, d) // "1 1 2 2"
// iota 常量生成器
type Weekday int // 定義一個Weekday 命名類型
const (
Sunday Weekday = iota
Monday
Tuesday
Wednesday
Thursday
Friday
Saturday
)
/* --> 七、模擬枚舉*/
type Weapon int // 定義新的數據結構體
const (
Arrow Weapon = iota // 開始生成枚舉值, 默認為0
Shuriken
SniperRifle
Rifle
Blower
)
// 輸出所有枚舉值,如上iota會從0依次增加
fmt.Println(Arrow, Shuriken, SniperRifle, Rifle, Blower) // 0 1 2 3 4
// 使用枚舉類型並賦初值
var weapon Weapon = Blower
fmt.Println(weapon) // 4
/*
1、注意:一個const聲明內的每一行常量聲明,將會自動套用前面的iota格式,並自動增加
*/
type ChipType int
const (
None ChipType = iota
CPU // 中央處理器
GPU // 圖形處理器
)
func (c ChipType) String() string {
switch c {
case None:
return "None"
case CPU:
return "CPU"
case GPU:
return "GPU"
}
return "N/A"
}
func main() {
// 輸出CPU的值並以整型格式顯示
fmt.Printf("%s %d", CPU, CPU)
}
/*
String() 方法的 ChipType 在使用上和普通的常量沒有區別。
當這個類型需要顯示為字符串時,Go語言會自動尋找 String() 方法並進行調用。
*/
/* --> 八、類型別名*/
// 將NewInt定義為int類型
type NewInt int
// 將int取一個別名叫IntAlias
type IntAlias = int
func main() {
var a NewInt
// 查看a的類型名
fmt.Printf("a type: %T\\n", a) // a type: main.NewInt
// 將a2聲明為IntAlias類型
var a2 IntAlias
// 查看a2的類型名
fmt.Printf("a2 type: %T\\n", a2) // a2 type: int
}
/*
結果顯示 a 的類型是 main.NewInt,表示 main 包下定義的 NewInt 類型,
a2 類型是 int,IntAlias 類型只會在代碼中存在,編譯完成時,不會有 IntAlias 類型。
*/
/* --> 九、字符串和數值類型的相互轉換*/
ltoa() // 整型轉字符串,函數簽名func Itoa(i int) string
Atoi() // 字符串轉整型,函數簽名func Atoi(s string) (i int, err error)
ParseBool() // 字符串轉換為bool類型值,函數簽名func ParseBool(str string) (value bool, err error)
Parselnt() // 字符串轉換為整數值(包括正負號),函數簽名func ParseInt(s string, base int, bitSize int) (i int64, err error)
ParseUnit() // 字符串轉換為整數值(不包括正負號),函數簽名func ParseUint(s string, base int, bitSize int) (n uint64, err error)
ParseFloat() // 浮點數字符串轉為float,函數簽名func ParseFloat(s string, bitSize int) (f float64, err error)
FormatBool() // bool類型轉換為字符串,函數簽名func FormatBool(b bool) string
FormatInt() // 整型轉換為字符串,函數簽名func FormatInt(i int64, base int) string
FormatUint() // 整型轉換為字符串(無符號的uint64類型),函數簽名func FormatUint(i uint64, base int) string
FormatFloat() // 浮點轉換為字符串,函數簽名func FormatFloat(f float64, fmt byte, prec, bitSize int) string
AppendBool() // append系列函數和format系列函數使用方法類似,append多了將轉換後結果追加到一個切片中
AppendFloat()
AppendInt()
AppendUint()
閱讀更多 消逝的初心 的文章