golang笔记
一、内存逃逸
本应在栈中内存,被分配到了堆中
1 返回指针对象 在外部被使用
2 reutrn 函数 使用了上面方法的敞亮
3 入参是interface{} 动态参数
4 make超过栈大小
-gcflags="-m"查看分配内存信息
返回变量vs返回指针
返回变量, 会多一步复制变量, 返回指针 复制指针, 如果有该对象内的属性 或者大对象的化 ,应分配到堆中, 反之返回变量
二、gc
1.3 标记清楚 - stw
1.5 三色标记 - 白 灰 黑,
并发操作时, 灰色指向白色 被断, 黑色可能直接引用白色
强三色 弱三色: 黑色不能直接指向白色 白色上游链路必须有灰色链路
写屏障 黑色引用白色, 白色置灰 stw
删除屏障, 灰色删除白色 白色置灰
缺点 栈的对象可能会频繁回收, 如果频繁屏障 难以接受
1.8 混合写屏障
gc开始时 栈中的对象标记黑
gc期间 新建的对象标记黑
堆中新建 标记灰色
删除的对象,标记灰色
三、gmp
Goroutine 协程 gomaxproes设置
Machine 物理内核
Procssor 协调管理器
Gmp模型, gotoutine 协程, machine 线程绑定物理内核, processor调度中心
初始化会有一个m0, 每一个线程会有g0, 创建g1时, 放到本地队列, g0调度g1运行,本地队列满时, 前半部打散和g1一起放到全局队列, p2 work stealing, 先从全局队列拿g,min (全局队列g的个数/maxgoprocs, 本地队列 / 2), 如果全局队列没有g, 从别的p的本地队列, stealing后一半 g, 如果g1 阻塞, hand off唤醒其他线程,和p绑定, 没有线程则放到全局队列, 阻塞完成后会优先抢p,如果p正在和其他线程执行, 放到全局队列
golang用法与关键字
1.变量声明
var a int
var a int = 100
var a = 100
a :=100 只能方法体内
var a b int = 100, 200
var a b = 100, “123”
var (
a int = 100
b bool = “123”
)
2.const iota
const length int = 100, length不可更改
const (
A = iota
B
C
)
iota 从0开始, 每行+1, iota只能配合const使用
3.func function1(a int, b string) (int, string) {}
4.init 与 import
5.go中unused限制
如果想只init()
import (
_ “lib2” // 匿名 只执行init()
. “lib3” lib3// 中所有方法导入到当前go 可以直接Test()
bieming “lib4” // lib4.Test()
)
6.defer 多个defer 压栈出栈形式, 先进后出
defer和return, 先return 后defer
7.切片
固定数组: var myArray [10]int , 传递时 值拷贝
var myArray [10]int{1,2,3}
for index, value := range myArray {}
动态数组 var myArray []int{1, 2, 3}, 传递时 传递指针
分配切片空间, slice1 := make([]int, 3), 分配3个空间
slice2 := make([]int, len, cap),
slice2 = append(slice2, 5)
append时超过原有cap, 开辟新空间, 新空间等于原来的cap
s3 := slice1[0, 2], [0, 2)左闭右开, s3也会指向slice1指针, slice1发生改变, s3同样发生改变
s4 := make([]int, 3)
copy(s4, slice1) slice1copy到s4里
8.map
myMap := make(map[string]string, cap), 也可以不加cap, 添加时候 会自动扩容
for key, value := range myMap {}
delete(myMap, “xxx”)
map传递时, 传递指针, 其他方法修改 全局生效
9.struct
封装:
type MyStruct struct {
Name string,
Author string
}
myS := MyStruct{Name: “xxx”, Author: “xxxx”}
func (my *MyStruct) (newName string) {
my.Name = newName
}
继承:
type NewStruct struct {
MyStruct // 代表继承MyStruct属性
age int
}
方法一: newStruct := NewStruct{MyStruct{ “xxxx”, “xxxxx”}, age: 10}
方法二: var newStruct NewStruct
newStruct.Name = “xxxx”
多态:
type AnimalIf interface {
GetColor string
GetType string
}
type Cat struct {
Color string
}
func (cat *Cat) GetColor string {
}
func (cat *Cat) GetType string {
}
var animal AnimalIf
animal := &Cat{Color: “yellow”}
animal.GetColor()
10.interface
interface{} 通用万能类型
value, ok := arg.(string)断言
channel
make(chan int) 无缓存通道,生产和消费必须同步,谁先到谁阻塞
make(chan int, cap) 有缓存通道, 生产者可以先生产, channel满, 生产者阻塞, channel为空,消费者阻塞