Go 语言拥有一些内置函数,内置函数是预先声明的,它们像任何其他函数一样被调用,内置函数没有标准的类型,因此它们只能出现在调用表达式中,它们不能用作函数值。
它们有时可以针对不同的类型进行操作:
内置函数 | 说明 |
---|---|
close | 用于通道,对于通道c,内置函数close(c)将不再在通道c上发送值。 如果c是仅接收通道,则会出错。 发送或关闭已关闭的通道会导致运行时错误。 关闭nil通道也会导致运行时错误。 |
new、make | new 和 make 均是用于分配内存:new用于值类型的内存分配,并且置为零值。make只用于slice、map以及channel这三种引用数据类型的内存分配和初始化。new(T) 分配类型 T 的零值并返回其地址,也就是指向类型 T 的指针。make(T) 它返回类型T的值(不是* T)。 |
make()内置函数声明不同类型时的参数以及具体作用请见下面说明:
调用 T的类型 结果
make(T, n) slice T为切片类型,长度和容量都为n
make(T, n, m) slice T为切片类型,长度为n,容量为m (n<=m ,否则错误)
make(T) map T为字典类型
make(T, n) map T为字典类型,初始化n个元素的空间
make(T) channel T为通道类型,无缓冲区
make(T, n) channel T为通道类型,缓冲区长度为n
make()
内置函数的实际使用举例见下面代码以及注释:
s := make([]int, 10, 100) // slice with len(s) == 10, cap(s) == 100
s := make([]int, 1e3) // slice with len(s) == cap(s) == 1000
s := make([]int, 1<<63) // illegal: len(s) is not representable by a value of type int
s := make([]int, 10, 0) // illegal: len(s) > cap(s)
c := make(chan int, 10) // channel with a buffer size of 10
m := make(map[string]int, 100) // map with initial space for approximately 100 elements
new(T)
内置函数在运行时为该类型的变量分配内存,并返回指向它的类型* T的值。 并对变量初始化。例如:
type S struct { a int; b float64 }
new(S)
new(S)
为S类型的变量分配内存,并初始化(a = 0,b = 0.0),返回包含该位置地址的类型* S的值。
内置函数 | 参数类型 | 结果 |
---|---|---|
len(s) | string type ,[n]T, *[n]T ,[]T ,map[K]T ,chan T | string的长度(按照字节计算),数组长度 ,切片长度 ,字典长度 ,通道缓冲区中排队的元素数 |
cap(s) | [n]T, *[n]T ,[]T ,chan T | 数组长度 ,切片容量 ,通道缓冲区容量 |
对于len(s)和cap(s),如果s为nil值,则两个函数的取值都是0,我们还需要记住一个规则:
0 <= len(s) <= cap(s)
在Go语言中,常量在某些计算条件下也可以通过表达式计算得到。比如:如果s是字符串常量,则表达式len(s)是常量。 如果s的类型是数组或指向数组的指针而表达式不包含通道接收或(非常量)函数调用,则表达式len(s)和cap(s)是常量;否则len和cap的调用不是常量。
const (
c1 = imag(2i) // imag(2i) = 2.0 是常量
c2 = len([10]float64{2}) // [10]float64{2} 无函数调用
c3 = len([10]float64{c1}) // [10]float64{c1} 无函数调用
c4 = len([10]float64{imag(2i)}) // imag(2i)常量无函数调用
c5 = len([10]float64{imag(z)}) // 无效: imag(z) 非常量函数调用
)
var z complex128
内置函数 | 说明 |
---|---|
append | 用于附加连接切片 |
copy | 用于复制切片 |
delete | 从字典删除元素 |
append(s S, x ...T) S // T 是类型S的元素
append内置函数是变参函数,常常用来附加切片元素,将零或多个值x附加到S类型的切片s,它的可变参数必须是切片类型,并返回结果切片,也就是是S类型。值x传递给类型为...的参数T,其中T 是S的元素类型,并且适用相应的参数传递规则:
s0 := []int{0, 0}
s1 := append(s0, 2) // append 附加连接单个元素 s1 == []int{0, 0, 2}
s2 := append(s1, 3, 5, 7) // append 附加连接多个元素 s2 == []int{0, 0, 2, 3, 5, 7}
s3 := append(s2, s0...) // append 附加连接切片s0 s3 == []int{0, 0, 2, 3, 5, 7, 0, 0}
s4 := append(s3[3:6], s3[2:]...) // append 附加切片指定值 s4 == []int{3, 5, 7, 2, 3, 5, 7, 0, 0}
var t []interface{}
t = append(t, 42, 3.1415, "foo") // t == []interface{}{42, 3.1415, "foo"}
var b []byte
b = append(b, "bar"...) // append 附加连接字符串内容 b == []byte{'b', 'a', 'r' }
copy(dst, src []T) int
copy(dst []byte, src string) int
copy内置函数常常将切片元素从源src复制到目标dst,并返回复制的元素数。 两个参数必须具有相同的元素类型T,并且必须可以分配给类型为[] T的切片。 复制的元素数量是len(src)和len(dst)的最小值。
作为特殊情况,copy函数还接受可分配给[] byte类型的目标参数,其中source参数为字符串类型。 此种情况将字符串中的字节复制到字节切片中。
var a = [...]int{0, 1, 2, 3, 4, 5, 6, 7}
var s = make([]int, 6)
var b = make([]byte, 5)
n1 := copy(s, a[0:]) // n1 == 6, s == []int{0, 1, 2, 3, 4, 5}
n2 := copy(s, s[2:]) // n2 == 4, s == []int{2, 3, 4, 5, 4, 5}
n3 := copy(b, "Hello, World!") // n3 == 5, b == []byte("Hello")
delete(m, k) //从字典m中删除元素 m[k]
内置函数delete从字典m中删除带有键k的元素。
内置函数 | 说明 |
---|---|
complex | 从浮点实部和虚部构造复数值 |
real | 提取复数值的实部 |
imag | 提取复数值的虚部 |
complex(realPart, imaginaryPart floatT) complexT
real(complexT) floatT
imag(complexT) floatT
内置函数complex用浮点实部和虚部构造复数值,而real和imag则提取复数值的实部和虚部。
对于complex,两个参数必须是相同的浮点类型,返回类型是具有相应浮点组成的复数类型。float32用于complex64参数,float64用于complex128参数。如果其中一个参数求值为无类型常量,则首先将其转换为另一个参数的类型。如果两个参数都计算为无类型常量,则它们必须是非复数或其虚部必须为零,并且函数的返回值是无类型复数常量。
对于real和imag,参数必须是复数类型,返回类型是相应的浮点类型:float32一般为complex64返回类型,float64一般为complex128返回类型。如果参数求值为无类型常量,则它必须是数字,并且函数的返回值是无类型浮点常量。
real和imag函数一起形成复数的逆,因此对于复数类型Z的值z,z == Z(complex(real(z),imag(z)))。
如果这些函数的操作数都是常量,则返回值是常量。
var a = complex(2, -2) // complex128
const b = complex(1.0, -1.4) // 无类型complex 常量 1 - 1.4i
x := float32(math.Cos(math.Pi/2)) // float32
var c64 = complex(5, -x) // complex64
var s uint = complex(1, 0) // 无类型 complex 常量 1 + 0i 可以转为uint
var rl = real(c64) // float32
var im = imag(a) // float64
const c = imag(b) // 无类型常量 -1.4
内置函数 | 说明 |
---|---|
panic | 用来表示非常严重的不可恢复的异常错误 |
recover | 用于从 panic 或 错误场景中恢复 |
func panic(interface{})
func recover() interface{}
panic和recover两个内置函数,协助报告和处理运行时异常和程序定义的错误。
在执行函数F时,显式调用panic或者运行时发生panic都会终止F的执行。然后,由F延迟(defer)的任何函数都照常执行。 依此类推,直到执行goroutine中的顶级函数延迟。 此时,程序终止并报告错误条件,包括panic参数的值。
panic(42)
panic("unreachable")
panic(Error("cannot parse"))
recover函数允许程序管理发生panic的goroutine的行为。
另外,Go语言中提供了几个在引导期间有用的内置函数。 这些函数不保证会保留在Go语言中,一般不建议使用。
print 打印所有参数
println 打印所有参数并换行
下一节:函数直接或间接调用函数本身,则该函数称为递归函数。