10 2021 档案
摘要:一、什么场景下需要用到锁当程序中就一个线程的时候,是不需要加锁的,但是通常实际的代码不会只是单线程,有可能是多个线程同时访问公共资源,所以这个时候就需要用到锁了,那么关于锁的使用场景主要涉及到哪些呢? 1. 多个线程在读相同的数据时2. 多个线程在写相同的数据时3. 同一个资源,有读又有写时 二、G
阅读全文
摘要:1. gomodules的初始化 2. 改变模块的依赖关系
阅读全文
摘要:0.1 GO module常用命令 go mod init # 初始化go.modgo mod tidy # 更新依赖文件go mod download # 下载依赖文件go mod vendor # 将依赖转移至本地的vendor文件go mod edit # 手动修改依赖文件go mod gra
阅读全文
摘要:1. 无缓冲通道 2. 有缓冲通道 有缓冲通道特点:当channel已经满,在向里面写数据就会阻塞,当channel已经为空,在从里面读数据就会阻塞。 3. 关闭channel package mainimport "fmt"func main() { c := make(chan int) go
阅读全文
摘要:goroutine与线程 /* goroutine与线程1. 可增长的栈os线程一般都有固定的栈内存,通常为2MB,一个goroutine的在其声明周期开始时只有很小的栈(2KB),goroutine的栈是不固定的,它可以按需增大或缩小,goroutine的栈大小限制可以达到1GB,虽然极少会用到这
阅读全文
摘要:package main import ( "fmt" "runtime" "time" ) func main() { // 用goroutine创建承载一个形参为空,返回值为空的一个函数 go func() { defer fmt.Println("A.defer") func() { defe
阅读全文
摘要:package main import ( "encoding/json" "fmt" "reflect" ) type Movie struct { Title string `json:"title"` Year int `json:"year"` Price int `json:"rmb"`
阅读全文
摘要:package main import ( "fmt" "reflect" ) type resume struct { // 反射解析结构体标签tag Name string `info:"name" doc:"我的名字"` Sex string `info:"sex"` } // 方法一:传递结
阅读全文
摘要:先重复一遍反射三定律: 1.反射可以将“接口类型变量”转换为“反射类型对象”。 2.反射可以将“反射类型对象”转换为“接口类型变量”。 3.如果要修改“反射类型对象”,其值必须是“可写的”(settable) 总结 下面详细说明了Golang的反射reflect的各种功能和用法,都附带有相应的示例,
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" ) func main() { // 静态文件服务 router := gin.Default() router.Static("/assets", "./assets") //
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" ) func main() { // HTTP重定向很容易,内部、外部重定向均支持 router := gin.Default() /* GET重定向 router.GET("/", func(cont
阅读全文
摘要:package main import ( "fmt" "reflect" ) type User struct { Id int Name string Age int } func (u User) Call() { fmt.Println("user is called.") fmt.Prin
阅读全文
摘要:package main import "fmt" type Reader interface { ReadBook() } type Writer interface { WriteBook() } // 具体类型 type Book struct {} func (b *Book) ReadBo
阅读全文
摘要:运行服务的返回类型为 :http.Handler 。gin.New(),gin.Default() 返回的就是此类型。使用&http.Server{....} 设置服务参数使用g.Go(func () error{ return server.ListenAndServe()}) 开启一个服务 pa
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" ) func main() { router := gin.Default() // 后台路由 admin := router.Group("/admin") admin.GET("/t1", func
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" ) func main() { router := gin.Default() // 路由参数1,将匹配/user/mayanan和/user/,但是不会匹配/user //router.G
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" ) func main() { router := gin.Default() router.GET("/cookie", func(context *gin.Context) { // 获
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "github.com/gin-gonic/gin/binding" "github.com/go-playground/validator/v10" "net/http" "time" ) type
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "log" "time" ) func Logger() gin.HandlerFunc { return func(context *gin.Context) { t := time.Now() //
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" "time" ) func main() { // 自定义http配置1 //router := gin.Default() //router.GET("/", func(cont
阅读全文
摘要:package main import "github.com/gin-gonic/gin" type StructA struct { FieldA string `form:"field_a"` } type StructB struct { // 嵌套结构体 NestedStruct Stru
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "log" "time" ) type Person struct { Name string `form:"name"` Address string `form:"address"` Birthda
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" ) type Person struct { Id string `uri:"id" binding:"required,uuid"` Name string `uri:"name
阅读全文
摘要:main.go package main import "github.com/gin-gonic/gin" type myForm struct { Colors []string `form:"colors[]"` } func main() { r := gin.Default() r.Loa
阅读全文
摘要:要将请求体绑定到结构体中,使用模型绑定。 Gin目前支持JSON、XML、YAML和标准表单值的绑定(foo=bar&boo=baz)。 Gin使用 go-playground/validator/v10 进行验证。 查看标签用法的全部文档. 使用时,需要在要绑定的所有字段上,设置相应的tag。 例
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" ) func main() { r := gin.Default() r.GET("/", func(context *gin.Context) { id := context.Q
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" ) func main() { r := gin.Default() r.GET("/", func(context *gin.Context) { // 查询字符串映射 (http://1
阅读全文
摘要:1. 一般通过调用 c.Request.Body 方法绑定数据,但不能多次调用这个方法。 package main import ( "fmt" "github.com/gin-gonic/gin" ) type FormA struct { Foo string `form:"foo" json:
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" "net/http" "time" ) func main() { router := gin.New() // LoggerWithFormatter middleware will wr
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "io" "os" ) func main() { // 禁用控制台颜色,将日志写入文件时不需要控制台颜色 gin.DisableConsoleColor() // 记录日志到文件 f, _ := os
阅读全文
摘要:1. 简单用法 package main import ( "github.com/gin-contrib/multitemplate" "github.com/gin-gonic/gin" "path/filepath" ) func createMyRender() multitemplate.
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" "log" "time" ) func main() { // 当在中间件或handler启动新的goroutine时, 不能使用原始的上下文,必须使用只读的副本 r := gin.Defa
阅读全文
摘要:Go 语言中会使用到的 25 个关键字或保留字: 1. 程序声明 import 导入 package 包 2. 程序实体声明和定义 chan 通道 var 变量声明 const 常量声明 func 用于定义函数和方法 interface 定义接口 map 字典/map struct 定义数据类型 t
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "log" ) type Person struct{ Name string `form:"name" binding:"required" json:"name"` Address string `
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" ) func main() { // 新建一个没有任何默认中间件的路由 router := gin.New() // Logger 中间件将日志写入 gin.DefaultWriter,即使
阅读全文
摘要:package mainimport ( "github.com/gin-gonic/gin" "net/http")// 模拟一些私人数据var secrets = gin.H{ "foo": gin.H{"email": "1341935532@qq.com", "phone": 1531306
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" "net/http" "reflect" ) func main() { // 从 reader 读取数据 router := gin.Default() router.GET("/some
阅读全文
摘要:1. 单文件上传 package main import ( "fmt" "github.com/gin-gonic/gin" "log" ) func main() { router := gin.Default() //为 multipart forms 设置较低的内存限制 (默认是 32 Mi
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "github.com/gin-gonic/gin/testdata/protoexample" ) func main() { router := gin.Default() router.GET("
阅读全文
摘要:使用 SecureJSON 防止 json 劫持。如果给定的结构是数组值或map,则默认预置 "while(1)," 到响应体。 package main import ( "github.com/gin-gonic/gin" ) func main() { router := gin.Defaul
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" ) func main() { r := gin.Default() // Query和PostForm r.GET("/post", func(c *gin.Context) { id := c.Qu
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" ) func main() { router := gin.Default() router.POST("/form_post", func(c *gin.Context) { // 接收post表单提
阅读全文
摘要:package main import ( "fmt" "github.com/gin-gonic/gin" "net/http" ) type LoginForm struct { // form:"user" 表示前端提交form表单时User对应的key的名称为:user // binding
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" ) func main() { r := gin.Default() r.GET("/jsonp", func(context *gin.Context) { data := ma
阅读全文
摘要:package main import ( "fmt" "io/fs" "io/ioutil" "os" "path" "path/filepath" ) func main() { // 文件和路径相关的功能包含了:os、path、filepath、ioutil包 // 1. 创建文件夹 // (
阅读全文
摘要:package main import ( "fmt" "regexp" ) func main() { // 1. 根据字符串匹配 m1, _ := regexp.MatchString("foo.*", "seafood") fmt.Println(m1) // true m2, _ := re
阅读全文
摘要:1. os.Args package main import ( "fmt" "os" ) func main() { // 执行:./demo.exe 127.0.0.1 8000 // 输出切片类型:[C:\Users\mayanan\Desktop\pro_go\day01\demo.exe
阅读全文
摘要:package main import ( "encoding/json" "fmt" "reflect" ) type Info struct { // 结构体的字段,首字母必须大写,否则序列化时读取不到 Title string Count int } type Address struct {
阅读全文
摘要:1. main包 package main import ( "day01/utils" "fmt" ) //type File struct { // fd int // name string //} //func NewFile(fd int, name string) *File { //
阅读全文
摘要:package main import "fmt" type Base struct { name string } func (b *Base) m1() int { return 666 } type Son struct { // 如果结构体之间存在匿名嵌套关系,则 子结构体 可以继承 父结构
阅读全文
摘要:package main import "fmt" // 项目开发中可以为type声明的类型编写一些方法,从而实现对象.方法的操作 // 声明类型 type myInt int // int有的功能myInt都有 // 为MyInt类型自定义一个指针方法 // 此处可以使指针,可以是类型 *myIn
阅读全文
摘要:1. 结构体做函数的参数或返回值时,都会被重新拷贝一份如果不想拷贝,可以传递结构体指针 package main import "fmt" type Person struct { name string age int } var p = Person{"武沛齐", 18} func doSome
阅读全文
摘要:1. 非闭包时的结果 package main import "fmt" func main() { var funcSlice []func() for i := 0; i < 5; i++ { // 此处匿名函数创建了,但是匿名函数中的内容根本没有执行 f := func() { fmt.Pri
阅读全文
摘要:package main import ( "fmt" "strconv" ) func main() { // 匿名函数的使用:方式1 f1 := func(n1, n2 int) string { return strconv.Itoa(n1 + n2) } ret1 := f1(11, 22)
阅读全文
摘要:package main import ( "github.com/gin-gonic/gin" "net/http" ) func login(ctx *gin.Context) { ctx.JSON(http.StatusOK, map[string]interface{}{ "username
阅读全文
摘要:gin是用于实时重新加载Go Web应用程序的简单命令行实用程序。只需gin在您的应用程序目录中运行,您的网络应用程序将 gin作为代理提供。gin检测到更改后,将自动重新编译您的代码。您的应用在下次收到HTTP请求时将重新启动。 gin 坚持“沉默就是黄金”的原则,因此,只有在出现编译器错误或在错
阅读全文
摘要:Gin 是一个用 Go (Golang) 编写的 web 框架。 它是一个类似于 martini 但拥有更好性能的 API 框架, 由于 httprouter,速度提高了近 40 倍。 如果你是性能和高效的追求者, 你会爱上 Gin. 特性 快速 基于 Radix 树的路由,小内存占用。没有反射。可
阅读全文
摘要:1. 函数当做函数的参数 package main import "fmt" type HandleFunc func(int) (int, bool) func add10(num1 int) (int, bool) { return num1 + 100, true } func proxy(d
阅读全文
摘要:### 下载指定版本 go get k8s.io/klog@v1.0.0 go get 命令可以借助代码管理工具通过远程拉取或更新代码包及其依赖包,并自动完成编译和安装。 这个命令在内部实际上分成了两步操作:第一步是下载源码包,第二步是执行 go install 参数介绍: -u 用于下载指定的路径
阅读全文
摘要:package main import ( "fmt" "sync" "time" ) /* 高并发是golang语言最大的亮点 一个线程可以包含多个协程,共享堆不共享栈 协程一般由应用程序显示实现调度,上下文切换不需下到内核层,高效不少 golang中实现协程间通讯有两种方式: (1)共享内存型:
阅读全文
摘要:package main import "fmt" func main() { /* 以下程序会导致死锁 c := make(chan int) c <- 10 n1 := <-c fmt.Println(n1) 为什么在同一个goroutine中使用无缓冲通道会导致死锁? 原因:1. 如果通道无缓
阅读全文
摘要:1. Channel是Go中的一个核心类型,你可以把它看成一个管道,通过它并发核心单元就可以发送或者接收数据进行通讯(communication)。 2. select package main import ( "fmt" "time" ) func fibonacci(c, quit chan
阅读全文
摘要:1. 概念 go中可以并发执行的活动单元称为goroutine当一个go程序启动时,一个执行main function的goroutine会被创建,称为main goroutinego func() 使用go语句开启一个新的goroutine之后,go语句之后的函数调用将在新的goroutine中执
阅读全文
摘要:GOPATH 是 Go 语言的工作目录,他的值可以是一个目录路径,也可以是多个目录路径,每个目录都代表 go 语言的一个工作区。 我们开发 Golang 项目时,需要依赖一些别的代码包,这些包的存放路径就与 GOPATH 有关。 在 v1.11 版本之前,所有的代码包都要放到 $GOPATH/src
阅读全文
摘要:package main import "fmt" func factorialFor(num int) (ret int) { // 循环求阶乘 ret = 1 for i := 1; i <= num; i++ { ret *= i } return } func factorialRecurs
阅读全文
摘要:package main import "fmt" // 一个函数中最多只可有一个可变参数, 如果参数列表中还有其它类型的参数,则可变参数写在最后 // 注意:参数不定,参数的个数是0-N个,也就是说可变参数可以为空 func sumNumber(num1 float64, nums ...floa
阅读全文
摘要:先理解:数组指针它的类型时指针,指针数组它的类型时数组 1. 数组指针当做函数的参数 package main import "fmt" func changeData(dataArray *[3]string) { // 数组指针当做函数参数 dataArray[1] = "马亚南" fmt.Pr
阅读全文
摘要:package main import "fmt" type human struct { name, phone string age int8 } type student struct { human // 嵌套结构体 school string } type employee struct
阅读全文
摘要:接口对象的转型有两种方式: 1. 方式一:instance,ok:=接口对象.(实际类型) 如果该接口对象是对应的实际类型,那么instance就是转型之后对象,ok的值为true 配合if...else if...使用 2. 方式二: 接口对象.(type) 配合switch...case语句使用
阅读全文
摘要:1. 在项目中实现注册成功之后,向用户发送邮件、微信提醒 package main import "fmt" type IMessage interface { send() bool } type Email struct { email string content string } func
阅读全文
摘要:package main import ( "fmt" ) type School struct { brand string city string } type Class struct { name string number int *School } func main() { // 创建
阅读全文
摘要:package main import ( "fmt" "reflect" ) func main() { // 如何获取结构体标签? type Person struct { name string "姓名" age int32 "年龄" blog string "博客" } p1 := Pers
阅读全文
摘要:p1是结构体,p2是结构体指针。 2. 声明并赋值结构体和结构体指针 package main import "fmt" type Person struct { name string age int } func main() { // 初始化结构体(创建一个结构体对象) p1 := Perso
阅读全文
摘要:package main import ( "fmt" "unsafe" ) func main() { // 根据内存地址获取下一个字节内存地址对应的值 dataList := [3]int8{11, 22, 33} // 1. 获取数组第一个元素的地址 var firstDataPtr *int
阅读全文
摘要:1. defer是go提供的一种资源处理的方式。defer的用法遵循3个原则在defer表达式被运算的同时,defer函数的参数也会被运算。如下defer的表达式println运算的同时,其入参i也会被运算,结果为初始化值0,故defer调用中会打印“0” package main import "
阅读全文
摘要:1. golang中的map有自己的一套实现原理,其核心是由hmap和bmap两个结构体实现的 2. 初始化map package main func main() { // 初始化一个可容纳10个元素的map map1 := make(map[string]string, 10) // 第一步:创
阅读全文
摘要:1. 声明与初始化 // map的声明与初始化 userInfo := map[string]string{"name": "马亚南", "age": "18"} fmt.Println(userInfo) fmt.Println(userInfo["name"]) // 马亚南 userInfo[
阅读全文
摘要:1. 切片中追加数据,如果没有扩容,内存地址不发生变化 // 1. 切片中追加数据,如果不扩容的话,内存地址不发生变化 v1 := make([]int, 1, 3) v2 := append(v1, 55) fmt.Println(v1, v2) fmt.Printf("%p, %p\n", &v
阅读全文
摘要:1. 数组的声明 package main import "fmt" func main() { // 数组:定长且元素类型一致的数据集合 // 方式一:先声明在赋值,声明时内存中已经开辟了空间 var nums [3]int // 内存中已开辟空间,初始化的值是0 nums[0] = 999 nu
阅读全文
摘要:1. 字符串的底层实现原理 package main import ( "fmt" "strconv" "unicode/utf8" ) func main() { // 计算机中所有的操作和数据最终都是二进制 // go语言中的字符串是utf-8编码的序列 // 字符串本质上是utf-8编码的序列
阅读全文
摘要:go get时由于防火墙的原因,会导致失败。目前可以通过修改GOPROXY的方法解决该问题。 无论是在win下还是linux,macos下,只需要将环境变量GOPROXY设置成https://goproxy.cn即可。可能还有别的代理可用。 有可能还需要设置GO111MODULE=on 具体在不同操
阅读全文
摘要:var price float32 = 39.29 float64和float32类似,只是用于表示各部分的位数不同而已,其中:sign=1位,exponent=11位,fraction=52位,也就意味着可表示的范围更大了。 二、decimal类型 由于golang中默认没有decimal类型,如
阅读全文
摘要:package main import ( "fmt" "math" ) func main() { fmt.Println(math.Abs(-19)) // 取绝对值 fmt.Println(math.Ceil(3.14)) // 向下取整 fmt.Println(math.Floor(3.14
阅读全文