github.com/haraldrudell/parl@v0.4.176/pslices/set-length.go (about)

     1  /*
     2  © 2023–present Harald Rudell <harald.rudell@gmail.com> (https://haraldrudell.github.io/haraldrudell/)
     3  ISC License
     4  */
     5  
     6  package pslices
     7  
     8  // SetLength adjusts the lenght of *slicep extending with append if necessary
     9  //   - slicep: pointer to slice whose length is adjusted
    10  //   - newLength : the length of *slicep on return
    11  //   - — if newLength > cap, slice may be reallocated
    12  //   - noZero missing or DoZeroOut: elements becoming unused are set to zero-value
    13  //   - — if element contain pointers, such elements are a temporary memory leak
    14  //   - noZero NoZeroOut: no zero-out of elements
    15  func SetLength[E any](slicep *[]E, newLength int, noZero ...bool) {
    16  
    17  	s := *slicep
    18  	length := len(s)
    19  	if newLength == length {
    20  		return // same length nothing to do return
    21  	}
    22  
    23  	doZero := true
    24  	if len(noZero) > 0 {
    25  		doZero = !noZero[0]
    26  	}
    27  
    28  	// shortening slice case
    29  	if newLength < length {
    30  		// zero out removed elements
    31  		if doZero {
    32  			var e E
    33  			for i := newLength; i < length; i++ {
    34  				s[i] = e
    35  			}
    36  		}
    37  		(*slicep) = s[:newLength]
    38  		return // slice shortened return
    39  	}
    40  
    41  	// extending with append case
    42  	if cap := cap(s); newLength > cap {
    43  		if length < cap {
    44  			s = s[:cap] // extend up to cap
    45  		}
    46  		*slicep = append(s, make([]E, newLength-cap)...)
    47  		return
    48  	}
    49  
    50  	// extending length within cap
    51  	s = s[:newLength]
    52  	if doZero {
    53  		var e E
    54  		for i := length; i < newLength; i++ {
    55  			s[i] = e
    56  		}
    57  	}
    58  	*slicep = s
    59  }