zoukankan      html  css  js  c++  java
  • Golang中的sync.Pool对象

      Golang中存在一个Sync.Pool 对象,从名字上看像是对象池,但他本质上和实际上的对象池有着很大的区别,下面将详细介绍该对象。 Sync.Pool对象可伸缩、并发安全;

    数据结构

    type Pool struct {
    	noCopy noCopy   //标识不可复制对象
    	local     unsafe.Pointer // 固定大小per-P池,实际类型[P] 
            PoolLocal
    	localSize uintptr        // local大小
    
    	victim     unsafe.Pointer // 来之上一个生命周期的指针,victim缓存
    	victimSize uintptr        //  victim大小
    	New func() interface{}
    }
    type poolLocalInternal struct {
    	private interface{}  // 私有空间,只能由局部调度器P使用		
    	shared  poolChain   // 共享空间,所有调度器P都可以进行相应操作,本地pushHead/popHead、任意P popTail
    }
    
    type poolLocal struct {
    	poolLocalInternal    // poolLocal 补齐至两个缓存行的倍数
            //每个缓存行具有 64 bytes,即 512 bit
            //处理器一般拥有 32 * 1024 / 64 = 512 条缓存行
            //一个poolLocal与一个P绑定,也就是说一个P持有一个poolLocal。每个 poolLocal 的大小均为缓存行的偶数倍。
    	pad [128 - unsafe.Sizeof(poolLocalInternal{})%128]byte
    }
    
    

      sync.Pool对外暴露Get、Put、New三个方法,Get返回Pool中的对象,当没有取得到对象时调用New创建新对象。Put将对象放入Pool中,这是对这三个方法的简单理解,集合Pool的实现下面将详细介绍;

    Sync.Pool对象获取

      对象的获取也就是调用Pool对象上面所说的Get方法,再执行Get方法时:
      1、先从私有的对象private中获取缓存对象,如获取失败从共享的shared中获取对象;
      2、如还是失败将尝试从victim中获取。
      3、从victim中获取对象失败,调用New方法;

    Sync.Pool对象加入

      将对象加入Pool中只需要调用Put方法即可,在执行Put方法时先尝试将对象放入私有的池private中,如private不为空这将对象放入共享的shared池中;

    sync.Pool对象生命周期

      Pool中对象的生命周期是不可控的,将有Go垃圾回收器进行管理,GC会清除sync.pool缓存的对象。1.13版本中引进的Victim对象可以理解为二次缓存。
      在第一次执行GC时会将对象放入victim中,在此的数据还是可以获取得到,当GC再此执行时victim中旧数据将被新淘汰得数据替换,此时数据彻底删除;
      Pool对象的缓存有效期为下下一次GC之前。

    p:= sync.Pool{New: func() interface{} {
    	return "2"
    }}
    fmt.Println(p.Get())    //输出2
    p.Put("123")
    p.Put("456")
    runtime.GC()         //清除123
    fmt.Println(p.Get())   //输出456
    

      对象生命周期无法掌控此机制的存在,所以sync.pool对象不适合用作对象池,因为无法控制GC也就无法掌握sync.pool中对象的生命周期;
      sync.Pool适合通过复用,降低复杂对象的创建和GC代价协程安全,生命周期受GC影响,不适合用于连接池等需要自己管理对象生命周期的池化。

  • 相关阅读:
    HttpWebRequest请求超时的解决方案!
    HttpWebRequest常用问题!
    System.IO 的三个抽象类
    枚举
    IINQ 的链接
    怎么样将sql server数据库中的结构导入到powerdesign中
    System.IO的三个静态类
    System.IO TextReader的二个子类
    学习序列化
    LookAndFeel枚举说明
  • 原文地址:https://www.cnblogs.com/softlin/p/12775801.html
Copyright © 2011-2022 走看看