gitee.com/sy_183/go-common@v1.0.5-0.20231205030221-958cfe129b47/pool/reference.go (about)

     1  package pool
     2  
     3  import "sync/atomic"
     4  
     5  type Reference interface {
     6  	Release() bool
     7  
     8  	AddRef()
     9  }
    10  
    11  type AtomicRef atomic.Int64
    12  
    13  func (r *AtomicRef) Release() bool {
    14  	if ref := (*atomic.Int64)(r).Add(-1); ref == 0 {
    15  		return true
    16  	} else if ref < 0 {
    17  		panic(NewInvalidReferenceError(ref, ref+1))
    18  	}
    19  	return false
    20  }
    21  
    22  func (r *AtomicRef) AddRef() {
    23  	if ref := (*atomic.Int64)(r).Add(1); ref <= 0 {
    24  		panic(NewInvalidReferenceError(ref, ref-1))
    25  	}
    26  }
    27  
    28  type RelationsReference interface {
    29  	Reference
    30  
    31  	AddRelation(relation Reference)
    32  
    33  	Clear()
    34  }
    35  
    36  type Relations struct {
    37  	AtomicRef
    38  	relations []Reference
    39  }
    40  
    41  func (r *Relations) AddRelation(relation Reference) {
    42  	r.relations = append(r.relations, relation)
    43  }
    44  
    45  func (r *Relations) Clear() {
    46  	for _, relation := range r.relations {
    47  		relation.Release()
    48  	}
    49  	r.relations = r.relations[:0]
    50  }
    51  
    52  func (r *Relations) Release() bool {
    53  	if r.AtomicRef.Release() {
    54  		r.Clear()
    55  		return true
    56  	}
    57  	return false
    58  }