2023年7月25日(暑假第四天)

今天下午才到家,所以今天学习的内容也要少一点点

go

1、走进go语法基础

2、go语言的实战案例

单词

今日学习了20个新单词

运动和娱乐

今日两公里加《巨额来电》

今日知识点

go语言的基础语法和特性

1 什么是go语言

  • 高性能,高并发

    • 不需要通过其它经过高度优化的第三方库来实现高并发

    • 通过go语言的标准库或者基于标准库开发的第三方库即可实现高并发

    • 有和c,c++,java媲美的性能

  • 语法简单,学习曲线平缓,学习周期短,几行代码即可实现一个承载静态文件装载的该并发

    扫描二维码关注公众号,回复: 16060519 查看本文章
    package main
    import(
    "net/http"
    )
    func main(){
        http.Handle("/",http.FileServer(http.Dir(".")))
            http.ListenAndServe(":8088",nil)
    }
  • 丰富的标准库

  • 完善的工具链

  • 静态链接

  • 快速编译,编译速度非常快

  • 跨平台(各种系统,各种奇奇怪怪的小东西)

  • 垃圾回收

2 入门

2.1.1 开发环境--安装Golang

打开go的官网,下载后安装提示进行安装即可

2.1.2 配置集成开发环境

可以选择VScode,GoLand

本人选择了vscode进行开发,通过左侧下载go的相关插件即可

2.2 基础语法

Hello World

package main
​
import (
    "fmt"
)
​
func main() {
    fmt.Print("hello world")
}
​
// 通过 go run demo.go即可运行
// 编译成二进制文件可以使用go build demo.go ,然后通过./demo运行exe文件

变量

package main
​
import (
    "fmt"
    "math"
)
​
func main() {
    var a = "initial"
    var b,c int = 1,2
    var d = true
    var e float64
    f := float32(e)
    g := a + "foo" // 可以通过==去比较字符串
    fmt.Println(a,b,c,d,e,f)
    fmt.Println(g)
​
    const s string = "constant" // 常量,没有确定的类型
    const h = 500000
    const i = 3e20 / h
    fmt.Println(s,h,math.Sin(h),math.Sin(i))
    // 常量最开始没有确定类型,而是根据使用的时候来确定
}

if-esle

package main
​
import (
    "fmt"
)
​
func main() {
    if 7%2 == 0 {
        fmt.Println("7 is even")
    } else {
        fmt.Println("7 is not even")
    }
​
    if 8%4 == 0 {
        fmt.Println("8 is not even")
    }
​
    if num := 9; num < 0 {
        fmt.Println(num, "is negative")
    } else if num < 10 {
        fmt.Println(num, "has 1 digit")
    } else {
        fmt.Println(num, "has mutiple digits")
    }
}

对于if-else,不同于c++,java等,条件里面不需要()

注意:if后面的内容必须重开一行,不能把if里面的东西写在同一行

循环

    for j := 7; j < 9; j++ {
        fmt.Println(j)
    }
    for n := 0; n < 5; n++ {
        if n%2 == 0 {
            continue
        }
        fmt.Println(n)
    }
    i := 1
    for i <= 3 {
        fmt.Println(i)
        i = i + 1
    }
​
    for {
        // 死循环
        fmt.Println("loop")
    }

switch

    a := 2
    switch a {
    case 1:
        {
            fmt.Println("one")
        }
    case 4, 5:
        {
            fmt.Println("four of five")
        }
    default:
        {
            fmt.Println("others")
        }
    }
​
    t := time.Now()
    switch {
    case t.Hour() < 12:
        fmt.Println("before afternoon")
    default:
        fmt.Println("after afternon")
    }

case不需要break,不会进行贯穿,通过case不仅仅可以是数字,还可以是其它的东西

数组和切片

    b := [5]int{1,2,3,4,5}
    var a [5]int
    a[4] = 100
    var twoD [2][3]int
​
    func main() {
        var t [2][3]int
        for i := 0; i < 2; i++ {
            for j := 0; j < 3; j++ {
                t[i][j] = i + j
            }
        }
        fmt.Println(t) // [[0 1 2] [1 2 3]]
    }
​
    s := make([]string, 3) // 切片
    s[0] = "a"
    s[1] = "b"
    s[2] = "c"
    fmt.Println("get", s[2])
    fmt.Println("len", len(s))
​
    s = append(s, "d")
    s = append(s, "e", "f")
    fmt.Println(s)
​
    c := make([]string, len(s))
    copy(c, s)
    fmt.Println(c)      // [a b c d e f]
    fmt.Println(s[2:5]) // [c d e]
    fmt.Println(s[:5])  //[a b c d e]
    fmt.Println(s[2:])  // [c d e f]
​
    good := []string{"g", "o", "o", "d"}
    fmt.Println(good) // [g o o d]

在go里面,其实数组很少使用,因为它长度固定了,通常都是使用切片,因为切片的长度是可以改变的。

切片是一个可变长度的数组,通过make创建一个切片

append必须把原数组的值赋值回去原数组

通过切片具有和python一样的切片操作

map(哈希,字典)

    m := make(map[string]int)
    m["one"] = 1
    m["two"] = 2
    fmt.Println(len(m))
    fmt.Println(m["one"])    // 1
    fmt.Println(m["unknow"]) // 0
​
    r, ok := m["unknow"] // ok表示这个map中是否含有这个键
    fmt.Println(r, ok) // 0 false
​
    m2 := map[string]int{
        "one": 1,
        "two": 2,
    }
    delete(m,"one")
    var m3 = map[string]int{
        "one": 1,
        "two": 2,
    }
    fmt.Println(m2, m3) // map[one:1 two:2] map[one:1 two:2]

就是其它语言的哈希,可以通过make进行创建

数据插入map后在map中是无序的

可以通过delete去删除K-V对

range

    nums := []int{2, 3, 4}
    sum := 0
    for i, num := range nums {
        sum += num
        if num == 2 {
            fmt.Println("index ", i, "num ", num)
        }
    }
    fmt.Println(sum)
​
    m := map[string]int{
        "one": 1,
        "two": 2,
    }
    for k, v := range m {
        fmt.Println(k, v)
    }
    for k := range m {
        fmt.Println("key", k)
    }

通过range我们可以对数组,切片,map等进行遍历

对于数组返回两个值,一个值是数组的索引,另一个是该索引下的值

函数

go里面变量类型是后知的,go的函数原生支持返回多个值,第一个值是真正的返回结果,第二个值是错误信息

import "fmt"
​
func add(a int, b int) (int, error) {
    return a + b, nil
}
​
func exists(m map[string]string, k string) (v string, ok bool) {
    v, ok = m[k]
    return v, ok
}
​
func main() {
    res, _ := add(1, 2)
    fmt.Println(res)
    v, ok := exists(map[string]string{"a": "A"}, "a")
    fmt.Println(v, ok)
}

指针

package main
​
import "fmt"
​
func add2(n int) {
    n += 2
}
​
func add2ptr(n *int) {
    *n += 2
}
​
func main() {
    n := 5
    add2(n)
    fmt.Println(n)
    add2ptr(&n)
    fmt.Println(n)
}
​

go语言里面的指针主要用途是对传入的参数进行修改

结构体

结构体是带类型和字段的集合,初始化时可以选择指定或者不指定结构体的内容,使用指针时可以在别的地方对值进行修改

​
type user struct {
    name     string
    password string
}
​
func main() {
    a := user{name: "wang", password: "123"}
    b := user{"wang", "123"}
    c := user{name: "wang"}
    c.password = "123"
    var d user
    d.name = "wang"
    d.password = "123"
    fmt.Println(a, b, c, d)
    fmt.Println(check2Password(&a, "haha"))
    fmt.Println(checkPassword(b, "123"))
}
func checkPassword(u user, password string) bool {
    return u.password == password
}
func check2Password(u *user, password string) bool {
    return u.password == password
}

当(u *user)提前后,该方法就从一个普通的方法变为一个结构体方法

func (u *user) resetPassword(password string){
    u.password = password
}

错误处理

在golang里面,通常使用一个带错误的返回值来对函数进行错误的处理

func findUser(users []user, name string) (v *user, err error) {
    for _, u := range users {
        if u.name == name {
            return &u, nil
        }
    }
    return nil, errors.New("not found")
}
​
func main() {
    u, err := findUser([]user{
  
  {"wang", "123"}}, "li")
    if err != nil {
        fmt.Println(err)
        return
    }
    fmt.Println(u.name)
}

在调用方法的时候,通过判断err是否为空来判断是否发生了错误

字符串操作

func main() {
    a := "Hello"
    fmt.Println(strings.Contains(a, "ll"))                // true
    fmt.Println(strings.Count(a, "l"))                    // 2
    fmt.Println(strings.HasPrefix(a, "he"))               // true
    fmt.Println(strings.HasSuffix(a, "llo"))              // true
    fmt.Println(strings.Index(a, "ll"))                   //2
    fmt.Println(strings.Join([]string{"he", "llo"}, "-")) // he-llo
    fmt.Println(strings.Repeat(a, 2))                     // hellohello
    fmt.Println(strings.Replace(a, "e", "E", -1))         // hEllo
    fmt.Println(strings.Split("a-b-c", "-"))              //[a b c]
    fmt.Println(strings.ToLower(a))                       // hello
    fmt.Println(strings.ToUpper(a))                       // HELLO
    fmt.Println(len(a))                                   // 5
    b := "你好"
    fmt.Println(len(b))
}

字符串格式化

func main() {
    s := "hello"
    n := 123
    p := point{1, 2}
    fmt.Println(s, n) // hello 123
    fmt.Println(p)    // 1 2
    fmt.Printf("s=%v\n", s)
    fmt.Printf("n=%v\n", n)
    fmt.Printf("p=%v\n", p)
    fmt.Printf("p=%+v\n", p)
    fmt.Printf("p=%#v\n", p)
    f := 3.14159
    fmt.Println(f)
    fmt.Printf("%0.2f\n", f)
}

%v可以代替任意类型的变量,%+v可以详细打印,%#v可以更加详细的打印

猜你喜欢

转载自blog.csdn.net/weixin_68798281/article/details/131928153