美文网首页Golanggo学习Golang 入门资料+笔记
build-webapp-with-go 前两章笔记(go 基础

build-webapp-with-go 前两章笔记(go 基础

作者: 暗黑破坏球嘿哈 | 来源:发表于2016-06-16 11:03 被阅读120次

    第一章

    go build带有main的文件
    go install包文件

    获取远程包
    go get github.com/astaxie/beedb
    -u update

    第二章

    • string内的值是不能被改变的,转为[]byte可以改变
    • map和其他基本型别不同,它不是thread-safe,在多个go-routine存取时,必须使用mutex lock机制
      //还没仔细看go-routine相关的内容,但是操作系统讲过什么是互斥锁
    • delete(rating, "C") // 删除map rating中key为C的元素
      //第二遍记这一点,不怎么用的东西真的是很难记得住
    • break操作是跳出当前循环,continue是跳过本次循环
      //之前无闻那篇笔记里非常快的带过了break和continue,开始写代码才发现都是很有用的东西,用得好会让代码好看简洁
    //代码来自astaxie
    for index := 10; index>0; index-- {
        if index == 5{
            break // 或者continue
        }
        fmt.Println(index)
    }
    // break打印出来10、9、8、7、6
    // continue打印出来10、9、8、7、6、4、3、2、1
    
    • switch中每个case里的执行语句后面默认是有break的,所以匹配后会自动跳出,不想跳出用fallthrough,每个case后可以跟多个值,case 2,3,4这样
    //代码来自astaxie
    i := 10
    switch i {
    case 1:
        fmt.Println("i is equal to 1")
    case 2, 3, 4:
        fmt.Println("i is equal to 2, 3 or 4")
    case 10:
        fmt.Println("i is equal to 10")
    default:
        fmt.Println("All I know is that i is an integer")
    }
    
    • 函数返回值声明了两个变量output1和output2,如果你不想声明也可以,直接就两个类型
      如果只有一个返回值且不声明返回值变量,那么你可以省略 包括返回值 的括号
      (注意:这样可以,但是不推荐,可读性降低!)

    • 函数类型,可以传递

    package main
    import "fmt"
    type testInt func(int) bool // 声明了一个函数类型
    func isOdd(integer int) bool {
    if integer%2 == 0 {
    return false
    }
    return true
    }
    func isEven(integer int) bool {
    if integer%2 == 0 {
    return true
    }
    return false
    }
    // 声明的函数类型在这个地方当做了一个参数
    func filter(slice []int, f testInt) []int {
    var result []int
    for _, value := range slice {
    if f(value) {
    result = append(result, value)
    }
    }
    return result
    }
    func main(){
    slice := []int {1, 2, 3, 4, 5, 7}
    fmt.Println("slice = ", slice)
    odd := filter(slice, isOdd) // 函数当做值来传递了
    fmt.Println("Odd elements of slice are: ", odd)
    even := filter(slice, isEven) // 函数当做值来传递了
    fmt.Println("Even elements of slice are: ", even)
    }

    * Panic
    是一个内建函数,可以中断原有的控制流程,进入一个令人恐慌的流程中。当函数F调用panic,函数F的执行被中断,但是F中的延迟函数会正常执行,然后F返回到调用它的地方。在调用的地方,F的行为就像调用了panic。这一过程继续向上,直到发生panic的goroutine中所有调用的函数返回,此时程序退出。恐慌可以直接调用panic产生。也可以由运行时错误产生,例如访问越界的数组。
    //摘录一段正经的panic介绍,虽然都大概知道这东西是干嘛的,但错误处理总是体现一个程序员的水平
    * Recovery
    是一个内建的函数,可以让进入令人恐慌的流程中的goroutine恢复过来。recover仅在延迟函数中有效。在正常的执行过程中,调用recover会返回nil,并且没有其它任何效果。如果当前的goroutine陷入panic,调用recovery可以捕获到panic的输入值,并且恢复正常的执行。
    * init和main函数不能有参数和返回值,且每包一个(init一包可以多个,但是强烈建议只写一个)
    * import 别名,“.”等别名都很简单,(提一点:_操作其实是引入该包,而不直接使用包里面的函数,而是调用了该包里面的init函数。)
    

    import (
    "database/sql"
    _ "github.com/ziutek/mymysql/godrv"
    )

    * struct声明方式
    三种
    
    

    type person struct{
    name string
    age int
    }
    //第一种
    var p person
    p.name="xy"
    p.age="18"
    //2
    p:= person{"xy",18}
    //3
    p:=new(person)

    //一个匿名字段的例子
    package main
    import "fmt"
    type Skills []string
    type Human struct {
    name string
    age int
    weight int
    phone string
    }
    type Student struct {
    Human // 匿名字段,struct
    Skills // 匿名字段,自定义的类型string slice
    int // 内置类型作为匿名字段
    speciality string
    phone string//human中也有phone字段
    }
    func main() {
    // 初始化学生Jane
    jane := Student{Human:Human{"Jane", 35, 100}, speciality:"Biology"}
    // 现在我们来访问相应的字段
    fmt.Println("Her name is ", jane.name)
    fmt.Println("Her age is ", jane.age)
    fmt.Println("Her weight is ", jane.weight)
    fmt.Println("Her speciality is ", jane.speciality)
    // 我们来修改他的skill技能字段
    jane.Skills = []string{"anatomy"}
    fmt.Println("Her skills are ", jane.Skills)
    fmt.Println("She acquired two new ones ")
    jane.Skills = append(jane.Skills, "physics", "golang")
    fmt.Println("Her skills now are ", jane.Skills)
    // 修改匿名内置类型字段
    jane.int = 3
    fmt.Println("Her preferred number is", jane.int)

    // 最外层的优先访问
    Bob := Employee{Human{"Bob", 34, "777-444-XXXX"}, "Designer", "333-222"}
    fmt.Println("Bob's work phone is:", Bob.phone)
    // 如果我们要访问Human的phone字段
    fmt.Println("Bob's personal phone is:", Bob.Human.phone)
    

    }

    
    * 值传递和引用传递
    >如果一个method的receiver是\*T,你可以在一个T类型的实例变量V上面调用这个method,而不需要&V去调用这个method;
    如果一个method的receiver是T,你可以在一个*T类型的变量P上面调用这个method,而不需要 *P去调用这个method
    
    * interface:Go通过interface实现了duck-typing:即"当看到一只鸟走起来像鸭子、游泳起来像鸭子、叫起来也像鸭子,那么这只鸟就可以被称为鸭子"。
    
    

    package main
    import "fmt"

    type Human struct {
    name string
    age int
    phone string
    }

    type Student struct {
    Human //匿名字段
    school string
    loan float32
    }

    type Employee struct {
    Human //匿名字段
    company string
    money float32
    }

    //Human实现SayHi方法
    func (h Human) SayHi() {
    fmt.Printf("Hi, I am %s you can call me on %s\n", h.name, h.phone)
    }

    //Human实现Sing方法
    func (h Human) Sing(lyrics string) {
    fmt.Println("La la la la...", lyrics)
    }

    //Employee重载Human的SayHi方法
    func (e Employee) SayHi() {
    fmt.Printf("Hi, I am %s, I work at %s. Call me on %s\n", e.name,
    e.company, e.phone)
    }

    // Interface Men被Human,Student和Employee实现
    // 因为这三个类型都实现了这两个方法
    type Men interface {
    SayHi()
    Sing(lyrics string)
    }

    func main() {
    mike := Student{Human{"Mike", 25, "222-222-XXX"}, "MIT", 0.00}
    paul := Student{Human{"Paul", 26, "111-222-XXX"}, "Harvard", 100}
    sam := Employee{Human{"Sam", 36, "444-222-XXX"}, "Golang Inc.", 1000}
    tom := Employee{Human{"Tom", 37, "222-444-XXX"}, "Things Ltd.", 5000}

    //定义Men类型的变量i
    var i Men
    
    //i能存储Student
    i = mike
    fmt.Println("This is Mike, a Student:")
    i.SayHi()
    i.Sing("November rain")
    
    //i也能存储Employee
    i = tom
    fmt.Println("This is tom, an Employee:")
    i.SayHi()
    i.Sing("Born to be wild")
    
    //定义了slice Men
    fmt.Println("Let's use a slice of Men and see what happens")
    x := make([]Men, 3)
    //这三个都是不同类型的元素,但是他们实现了interface同一个接口
    x[0], x[1], x[2] = paul, sam, mike
    
    for _, value := range x{
        value.SayHi()
    }
    

    }

    
    * element.(type)语法不能在switch外的任何逻辑里面使用,如果你要在switch外面判断一个类型就使用comma-ok(if value, ok := element.(int); ok {...})
    * reflection
    var x float64 = 3.4
    p := reflect.ValueOf(&x)
    v := p.Elem()
    v.SetFloat(7.1)

    相关文章

      网友评论

      • 76910291d56f:这本书还不错
        暗黑破坏球嘿哈:@76910291d56f 是的,不过我有点急用简单的部分,所以目前只看了前面,后面好像在讲beego,暂时用不到

      本文标题:build-webapp-with-go 前两章笔记(go 基础

      本文链接:https://www.haomeiwen.com/subject/cjlpdttx.html