错误处理
在 go 语言里面符合语言习惯的做法就是使用一个单独的返回值来传递错误信息。不同于Java 自家家使用的异常。go语言的处理方式,能够很清晰地知道哪个函数返回了错误,并且能用简单的 if else 来处理错误,在函数里面,我们可以在那个函数的返回值类型里面,后面加一个 error, 就代表这个函数可能会返回错误。那么在函数实现的时候,retumn 需要同时reum 两个值,要么就是如果出现错误的话,那么可以retumn nil 和一个error。如果没有的话,那么返回原本的结果和 nil.
我在这里解释一下nil是什么
在Go语言中,nil 是一个预定义的标识符,用于表示指针、接口、切片、映射、通道和函数类型的零值。具体来说:
- 对于指针类型,
nil表示一个不指向任何有效内存地址的指针。 - 对于接口类型,
nil表示一个不包含任何值的接口。 - 对于切片、映射和通道类型,
nil表示一个未初始化的值,即没有内存被分配给这些类型。 - 对于函数类型,
nil表示一个不指向任何函数的函数类型。
我在这里再解释一下 error在golang中的含义
在Go语言中,error 是一个内置的接口类型。这个接口定义了一个方法 Error() string,任何实现了这个方法的类型都可以被视为一个 error 类型。
*可以使用for循环和range关键字来遍历切片中的元素。range关键字会返回两个值:当前迭代的索引和切片中的对应元素值。如果你不需要索引,可以使用_来忽略它。
for _, u := range users {
if u.name == name {
return &u, nil
}
}
return nil, errors.New("not found")
}
func main() {
u, err := findUser([]user{{"wang", "1024"}}, "wang")
if err != nil {
fmt.Println(err)
return
}
fmt.Println(u.name) // wang
if u, err := findUser([]user{{"wang", "1024"}}, "li"); err != nil {
fmt.Println(err) // not found
return
} else {
fmt.Println(u.name)
}
}
字符串操作
字符串匹配函数
fmt.Println(strings.Contains(a, "ll")):检查字符串a是否包含子串"ll"。fmt.Println(strings.Count(a, "l")):计算字符串a中"l"出现的次数。fmt.Println(strings.HasPrefix(a, "he")):检查字符串a是否以"he"为前缀。fmt.Println(strings.HasSuffix(a, "llo")):检查字符串a是否以"llo"为后缀。fmt.Println(strings.Index(a, "ll")):返回字符串a中第一次出现"ll"的位置。fmt.Println(strings.Join([]string{"he", "llo"}, "-")):使用指定的分隔符-连接字符串数组。fmt.Println(strings.Repeat(a, 2)):将字符串a重复指定次数2。fmt.Println(strings.Replace(a, "e", "E", -1)):将字符串a中的所有"e"替换为"E"。fmt.Println(strings.Split("a-b-c", "-")):使用指定的分隔符-将字符串分割成字符串数组。fmt.Println(strings.ToLower(a)):将字符串a转换为小写形式。fmt.Println(strings.ToUpper(a)):将字符串a转换为大写形式。fmt.Println(len(a)):返回字符串a的长度。
字符串格式化示例
这些语句都是使用fmt.Printf函数来格式化输出数据。
-
fmt.Printf("s=%v\n", s):- 输出字符串
s的值,并在前面加上前缀s=。 %v是一个格式化动词,用于打印任何类型的值。\n是一个转义字符,表示换行。
- 输出字符串
-
fmt.Printf("n=%v\n", n):- 输出整数
n的值,并在前面加上前缀n=。 - 同样使用
%v来打印整数值。
- 输出整数
-
fmt.Printf("p=%v\n", p):- 输出结构体
p的值,并在前面加上前缀p=。 - 结构体
p的类型是point,包含两个字段x和y。 - 使用
%v来打印结构体的值,会输出结构体的字段名和对应的值。
- 输出结构体
-
fmt.Printf("p=%+v\n", p):- 输出结构体
p的值,并在前面加上前缀p=。 - 使用
%+v来打印结构体的值,会输出结构体的字段名和对应的值,并且会在字段名前面加上字段的名称。
- 输出结构体
-
fmt.Printf("p=%#v\n", p):- 输出结构体
p的值,并在前面加上前缀p=。 - 使用
%#v来打印结构体的值,会输出结构体的字段名和对应的值,并且会在字段名前面加上结构体的类型名和字段的名称。
- 输出结构体
这些格式化动词可以帮助你更清晰地输出数据,特别是在调试和查看复杂数据结构时非常有用。
JSON
JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,它基于JavaScript的一个子集,易于人阅读和编写,同时也易于机器解析和生成。JSON通常用于在不同的编程语言和系统之间传输数据。
JSON的格式非常简单,它由两种结构组成:
- 对象(Object) :一个对象是一个无序的键值对集合。在JSON中,对象以
{开始,以}结束。每个键值对之间用,分隔,键和值之间用:分隔。键必须是字符串,而值可以是字符串、数字、布尔值、对象或数组。 - 数组(Array) :一个数组是一个有序的值的集合。在JSON中,数组以
[开始,以]结束。值之间用,分隔。
时间处理
最常用的:time.now (用来获取当前时间)
``` now := time.Now()
fmt.Println(now) // 2022-03-27 18:04:59.433297 +0800 CST m=+0.000087933
t := time.Date(2022, 3, 27, 1, 25, 36, 0, time.UTC)
t2 := time.Date(2022, 3, 27, 2, 30, 36, 0, time.UTC)
fmt.Println(t) // 2022-03-27 01:25:36+0000 UTC
fmt.Println(t.Year(), t.Month(), t.Day(), t.Hour(), t.Minute()) // 2022 March 27 1 25
fmt.Println(t.Format("2006-01-02 15:04:05")) // 2022-03-27 01:25:36
diff := t2.Sub(t)
fmt.Println(diff) // 1h5m0s
fmt.Println(diff.Minutes(), diff.Seconds()) // 65 3900
t3, err := time.Parse("2006-01-02 15:04:05", "2022-03-27 01:25:36")
if err != nil {
panic(err)
}
fmt.Println(t3 == t) // true
fmt.Println(now.Unix()) // 1648738080时间戳```
数字解析
n, _ := strconv.ParseInt("111", 10, 64)//第一个操作数代表数字本身,第二个代表是十进制,第三个代表占多少位。
字符串数字转换:
这段代码主要展示了如何使用Go语言标准库中的strconv包来进行字符串到整数的转换。具体来说,它使用了Atoi函数,这个函数可以将一个字符串转换为一个整数。大前提是要包含这个包import{"strconv"}
fmt.Println(n2) // 123
n2, err := strconv.Atoi("AAA")
fmt.Println(n2, err) // 0 strconv.Atoi: parsing "AAA": invalid syntax
获取golang中的进程信息
在 golang 里面,我们能够用 os.argv 来得到进程执行的时候的指定的命令行参数。 比如我们编译的一个二进制文件,command。后面接 abcd 来启动,输出就是 os.argv 会是一个长度为5的 slice,一个成员代表二进制自身的名字。可以用 so.getenv来读取环境变量。
fmt.Println(os.Args)
fmt.Println(os.Getenv("PATH"))
fmt.Println(os.Setenv("AA", "BB"))