package regexp2

import (
	
	
	
)

type pooledSliceBuffers[ any] struct {
	sizes []int
	pools []sync.Pool
}

func newPooledSliceBuffers[ any]( ...int) *pooledSliceBuffers[] {
	 = slices.Clone()
	slices.Sort()
	return &pooledSliceBuffers[]{
		sizes: ,
		pools: make([]sync.Pool, len()),
	}
}

func ( *pooledSliceBuffers[]) (,  int) int {
	if  == 0 {
		return -1
	}
	for ,  := range .sizes {
		if  <=  {
			if  > 0 &&  >  {
				return -1
			}
			return 
		}
	}
	return -1
}

func ( *pooledSliceBuffers[]) (,  int) ([], *[]) {
	 := .poolIndex(, )
	if  < 0 {
		return make([], ), nil
	}
	if  := .pools[].Get();  != nil {
		 := .(*[])
		if cap(*) >=  {
			return (*)[:], 
		}
	}
	 := make([], , .sizes[])
	return , &
}

func ( *pooledSliceBuffers[]) ( *[]) {
	 := .poolIndex(cap(*), -1)
	if  < 0 || cap(*) != .sizes[] {
		return
	}
	* = (*)[:0]
	.pools[].Put()
}

// our specific pooled buffers
var (
	pooledRuneBuffers = newPooledSliceBuffers[rune](1<<10, 4<<10, 16<<10, 64<<10, 256<<10)
	pooledByteBuffers = newPooledSliceBuffers[byte](4<<10, 16<<10, 64<<10, 256<<10, 1<<20)
)

func getPooledReplaceBuffer(,  int) (*bytes.Buffer, *[]byte) {
	,  := pooledByteBuffers.get(, )
	return bytes.NewBuffer([:0]), 
}

func putPooledReplaceBuffer( *bytes.Buffer,  *[]byte) {
	* = .Bytes()
	pooledByteBuffers.put()
}