整型
Go
语言提供多个整数类型,根据计算架构可分为有符号整数类型 int
和无符号整数类型 uint
:
- 在 32 位操作系统中,
int
或uint
使用 32 个bit
表示数值,即 4 个字节; - 在 64 位操作系统中,
int
或uint
使用 64 个bit
表示数值,即 8 个字节。
除了这两个和计算架构有关的整数类型外,还有 8 个和操作系统无关、显式表示宽度的整数类型:
整数范围 | 符号 | 宽度(bit ) | 范围 |
---|---|---|---|
int8 | 有 | 8 | -128 ~ 127 |
int16 | 有 | 16 | -32768 ~ 32767 |
int32 | 有 | 32 | -2,147,483,648 ~ 2,147,483,647 |
int64 | 有 | 64 | -9,223,372,036,854,775,808 ~ 9,223,372,036,854,775,807 |
uint8 | 无 | 8 | 0 ~ 255 |
uint16 | 无 | 16 | 0 ~ 65535 |
uint32 | 无 | 32 | 0 ~ 4,294,967,295 |
uint64 | 无 | 64 | 0 ~ 18,446,744,073,709,551,615 |
int
类型的最高位的bit
表示正负,所以其表示的整数范围缩小了,而uint
使用所有比特位表示数值。
另外,还有一个整数类型:
uintptr
,没有指定具体的bit
大小但是足以容纳指针,只有在底层编程时才用到,特别是Go
语言和C
语言函数库或操作系统接口相交互的地方。
rune 和 byte
rune
和 int32
等价,可以看作 int32
的别名类型,byte
则和 uint8
等价。
一个 rune
类型可表示一个 Unicode
字符,也就是 Unicode
代码点。一个 Unicode
代码点通常由 U+
和一个以十六进制表示法表示的整数表示。例如,英文字母 A
的 Unicode
代码点为 U+0041
。
8 进制和 16 进制
- 增加前缀
0
来表示 8 进制数,如:077
- 增加前缀
0x
或0X
来表示 16 进制数,如:0xFF
a, b := 077, 0xFF
fmt.Printf("%o %X", a, b) //77 FF
复制代码
浮点型
Go
提供两种精度的浮点类型:float32
和 float64
,存储这两个类型的值的空间分别需要 4 个字节和 8 个字节。浮点数范围极限值可以在 math
包找到:math.MaxFloat32
、math.MaxFloat64
:
类型 | 范围 |
---|---|
float32 | 约 1.4e-45 ~ 3.4e38 |
float64 | 约 4.9e-324 ~ 1.8e308 |
float32
精确到小数点后 7 位,float64
精确到小数点后 15 位。由于精确度的缘故,在使用 ==
或者 !=
来比较浮点数时应当非常小心。
因为 float32
的有效 bit
位只有 23 个,其它的 bit
位用于指数和符号,当整数大于 23bit
能表达的范围时,float32
的表示将出现误差。所以应该尽量使用 float64
,因为 math
包中所有有关数学运算的函数都会要求接收这个类型。
注意,没有
float
类型。
表示方法
-
小数点表示:
var a float64 = 1.2
-
科学计数法(
E
或e
皆可):var a float64 = 3.7E-2 fmt.Println(a == 0.037) // true var b float64 = 2.3e+3 // 或 2.3e3 fmt.Println(b == 2300) // true 复制代码
注意:
- 在
Go
语言中,浮点数的相关部分只能由 10 进制表示法表示,而不能由 8 进制表示法或 16 进制表示法表示。比如,03.7
表示的一定是浮点数3.7
;
复数
Go
语言有两种精度的复数类型:complex64
和 complex128
,存储这两个复数类型的值分别需要 8 和 16 个字节。
complex64
类型的值由两个 float32
类型的值分别表示复数的实数部分和虚数部分;而 complex128
类型的值由两个 float64
类型的值分别表示复数的实数部分和虚数部分。
// 定义复数
var a complex64 = 10 + 5i // 10+5i
var b complex64 = complex(2, 3) // 2+3i
// 获取实数和虚数部分
fmt.Println(real(a), real(b)) // 10 2,float32 类型
fmt.Println(imag(a), imag(b)) // 5 3,float32 类型
复制代码
使用
==
或!=
对复数进行比较运算时,注意精确度。
如果对内存的要求不是特别高,最好使用
complex128
类型,因为相关函数都使用这个类型的参数。
布尔型
- true
- false
var a bool = true
b := false
复制代码
字符串
一个字符串类型的值可以代表一个字符序列,Go
使用 UTF-8
将字符串(或者说字符序列)编码为字节数组。
注意,使用内置函数
len
会得到字节数组的长度,而不是表面上的长度。
表示
- 解释字符串:使用双引号括起来,其中的相关的转义字符将被替换;
- 原生字符串:使用反引号括起来,其中的值是所见即所得的(除了回车符)。
解释字符串中的转义字符包括:
\n
:换行符\r
:回车符\t
:tab
键\u
或\U
:Unicode
字符\\
:反斜杠自身- ......
索引
对于 ASCII
字符串,可以通过索引来获取其内容:
str[0]
:第 1 个字节str[i - 1]
:第 i 个字节str[len(str)-1]
:最后 1 个字节(不支持负数索引)s[i:j]
:第 i 个字节到第 j 个字节(不包含 j 本身)- 超出索引范围会导致
panic
异常 &str[i]
:错误,获取字符串中某个字节的地址的行为是非法的。
a := "hello"
fmt.Printf("%q\n", a[0]) // h
fmt.Printf("%q\n", a[4]) // 0
fmt.Printf("%q\n", a[0:5]) // hello,不包括a[5]
fmt.Printf("%q\n", a[:4]) // hell,不包括a[4]
fmt.Printf("%q\n", a[2:]) // llo
复制代码
拼接
s1 := "hello" + " world"
// 由于编译器行尾自动补全分号的缘故,+ 必须放在第一行
s2 := "hello" +
" world"
复制代码
当涉及到大量拼接操作时,+
并不高效,更好的方法是使用函数 strings.Join()
,字节缓冲 bytes.Buffer
拼接效率还要更高。
strings
strings
中有很多操作字符串的方法,使用 strings.HasPrefix
的形式调用:
-
HasPrefix(s, prefix string) bool
:判断字符串s
是否以prefix
开头 -
HasSuffix(s, suffix string) bool
:判断字符串s
是否以suffix
结尾 -
Contains(s, substr string) bool
:判断字符串s
是否包含substr
-
Index(s, str string) int
:返回字符串str
在的首个字符在字符串s
中的首次出现的位置的索引,-1
表示字符串s
不包含字符串str
-
LastIndex(s, str string) int
: 返回字符串str
在的首个字符在字符串s
中的最后出现的位置的索引,-1
表示字符串s
不包含字符串str
-
IndexRune(s string, r rune) int
:查询非ASCII
编码的字符在父字符串中的位置 -
Replace(str, old, new, n) string
:字符串替换,将字符串str
中的前n
个字符串old
替换为字符串new
,并返回一个新的字符串,如果n = -1
则替换所有字符串old
为字符串new
-
Count(s, str string) int
:用于计算字符串str
在字符串 s 中出现的非重叠次数 -
Repeat(s, count int) string
:用于重复count
次字符串s
并返回一个新的字符串 -
ToLower(s) string
:转换为小写 -
ToUpper(s) string
:转换为大写 -
Trim(s string, cutset string) string
:删除头尾指定的Unicode
字符 -
TrimLeft(s string, cutset string) string
:删除头部指定的Unicode
字符 -
TrimRight(s string, cutset string) string
:删除尾部指定的Unicode
字符 -
TrimSpace(s string) string
:删除头尾的空格 -
TrimPrefix(s, prefix string)
:返回头部去掉prefix
的字符串 -
TrimSuffix(s, suffix string) string
:返回尾部去掉suffix
的字符串 -
Fields(s string) []string
:使用空白符(包括连续的空白符)将字符串s
切割为一个slice
-
strings.Split(s, sep) []string
:使用sep
作为分割符对s
进行分割,返回slice
-
strings.Join(sl []string, sep string) string
:将元素类型为string
的slice
使用分割符号sep
来拼接组成一个字符串。 -
NewReader(str)
:生成一个Reader
并读取字符串中的内容,然后返回指向该Reader
的指针。类似Read()
从[]byte
中读取内容,ReadByte()
和ReadRune()
从字符串中读取下一个byte
或者rune
。
strconv
strconv
处理字符串与其它类型的转换。
strconv.IntSize
:获取当前平台下int
类型所占的位数- 任何类型 T 转换为字符串都可以
- 将字符串转换为其它类型并不总是都可以
格式化打印
fmt
包中的几个打印方法:
方法 | 说明 |
---|---|
Print | 输出到控制台(不接受任何格式化,它等价于对每一个操作数都应用 %v |
Println | 输出到控制台并换行 |
Printf | 格式化打印输出。注意,如果不用占位符,直接使用此方法,只能输出字符串类型的变量。 |
Sprintf | 格式化并返回一个字符串,不会打印 |
Fprintf | 来格式化并输出到 io.Writers 而不是 os.Stdout |
适用类型 | 占位符 | 说明 |
---|---|---|
普通 | %v | 值的默认格式 |
%+v | 添加字段名,如结构体 | |
%#v | Go语法表示 | |
%T | 相应值的类型的Go语法表示 | |
%% | 字面上的百分号 | |
整型 | %b | 二进制表示 |
%c | 相应Unicode码点所表示的字符 | |
%d | 十进制表示 | |
%o | 八进制表示 | |
%q | 单引号围绕的字符字面值,由Go语法安全地转义 | |
%x | 十六进制表示,字母形式为小写 a-f | |
%X | 十六进制表示,字母形式为大写 A-F | |
%U | Unicode格式:U+1234,等同于 "U+%04X" | |
浮点数及复数 | %b | 无小数部分的,指数为二的幂的科学计数法,与 strconv.FormatFloat 中的 'b' 转换格式一致。例如 -123456p-78 |
%e | 科学计数法,例如 -1234.456e+78 | |
%E | 科学计数法,例如 -1234.456E+78 | |
%f | 小数点表示法,如 1.23 | |
%g | 根据情况选择 %e 或 %f 以产生更紧凑的(无末尾的0)输出 | |
%G | 根据情况选择 %E 或 %f 以产生更紧凑的(无末尾的0)输出 | |
字符串和字节切片 | %s | 字符串或切片的无解译字节 |
%q | 双引号围绕的字符串,由Go语法安全地转义 | |
%x | 十六进制,小写字母,每字节两个字符 | |
%X | 十六进制,大写字母,每字节两个字符 | |
指针 | %p | 十六进制表示,前缀 0x |
布尔型 | %t | true 或 false |
其它 | + | 打印数值的正负号;对于%q(%+q)保证只输出ASCII编码的字符 |
- | 在右侧填充空格(左对齐) | |
# | %#b、%#o、%#x 添加前缀打印;%#q :打印原始 (即反引号围绕的)字符串;%#U :打印 Unicode 编码形式 | |
空格 | 为数值中省略的正负号留出空白(% d) |