amuz.es/src/go/misc@v1.0.1/strutil/format.go (about) 1 package strutil 2 3 import ( 4 "math" 5 "strings" 6 ) 7 8 // FillBytes fill the destination byte array with the given pattern. 9 func FillBytes(dst []byte, pattern []byte) { 10 for i := 0; i < len(dst); i++ { 11 dst[i] = pattern[i%len(pattern)] 12 } 13 } 14 15 // FillByte fills the destination byte array with a single byte. 16 func FillByte(dst []byte, pattern byte) { 17 for i := 0; i < len(dst); i++ { 18 dst[i] = pattern 19 } 20 } 21 22 // StrPad method pads the input string with the padString until the resulting string reaches the given length 23 func StrPad(input string, padLength int, padString string, rightPad bool) (output string) { 24 var ( 25 inputLength = len(input) 26 padStringLength = len(padString) 27 ) 28 if inputLength >= padLength { 29 return input 30 } 31 32 var ( 33 repeat = int(math.Ceil(float64(1) + (float64(padLength-padStringLength))/float64(padStringLength))) 34 builder strings.Builder 35 ) 36 builder.Grow(inputLength + padStringLength*repeat) 37 if rightPad { 38 builder.WriteString(input) 39 for i := 0; i < repeat; i++ { 40 builder.WriteString(padString) 41 } 42 output = builder.String()[:padLength] 43 } else { 44 for i := 0; i < repeat; i++ { 45 builder.WriteString(padString) 46 } 47 builder.WriteString(input) 48 output = builder.String()[builder.Len()-padLength:] 49 } 50 51 return 52 } 53 54 // StrPadSingle method pads the input string with a single character until the resulting string reaches the given length 55 func StrPadSingle(input string, padLength int, pad byte, rightPad bool) (output string) { 56 var ( 57 inputLength = len(input) 58 ) 59 if inputLength >= padLength { 60 return input 61 } 62 63 var ( 64 builder strings.Builder 65 ) 66 builder.Grow(inputLength + padLength) 67 if rightPad { 68 builder.WriteString(input) 69 for i := 0; i < padLength; i++ { 70 builder.WriteByte(pad) 71 } 72 output = builder.String()[:padLength] 73 } else { 74 for i := 0; i < padLength; i++ { 75 builder.WriteByte(pad) 76 } 77 builder.WriteString(input) 78 output = builder.String()[builder.Len()-padLength:] 79 } 80 81 return 82 } 83 84 // BytesPad method pads the input byte array with the padData byte array until the resulting string reaches the given length 85 func BytesPad(input []byte, padLength int, padData []byte, rightPad bool) (output []byte) { 86 var ( 87 inputLength = len(input) 88 padDataLength = len(padData) 89 ) 90 if inputLength >= padLength { 91 output = make([]byte, inputLength) 92 copy(output, input) 93 return 94 } 95 96 var ( 97 repeat = int(math.Ceil(float64(1) + (float64(padLength-padDataLength))/float64(padDataLength))) 98 maxFillLength = repeat * padDataLength 99 bufSize = inputLength + repeat*padDataLength 100 padArea, fillArea []byte 101 ) 102 103 output = make([]byte, bufSize) 104 105 if rightPad { 106 fillArea, padArea = output[0:inputLength], output[inputLength:bufSize] 107 output = output[:padLength] 108 } else { 109 fillArea, padArea = output[maxFillLength:bufSize], output[0:maxFillLength] 110 output = output[inputLength+maxFillLength-padLength:] 111 } 112 113 // copy data 114 copy(fillArea, input) 115 // fill pad 116 for i := 0; i < repeat; i++ { 117 copy(padArea[:padDataLength], padData) 118 padArea = padArea[padDataLength:] 119 } 120 121 return 122 } 123 124 // BytesPad method pads the input byte array with a single byte until the resulting string reaches the given length 125 func BytesPadSingle(input []byte, padLength int, pad byte, rightPad bool) (output []byte) { 126 var ( 127 inputLength = len(input) 128 ) 129 if inputLength >= padLength { 130 output = make([]byte, inputLength) 131 copy(output, input) 132 return 133 } 134 135 var ( 136 maxFillLength = padLength 137 bufSize = inputLength + padLength 138 padArea, fillArea []byte 139 ) 140 141 output = make([]byte, bufSize) 142 143 if rightPad { 144 fillArea, padArea = output[0:inputLength], output[inputLength:bufSize] 145 output = output[:padLength] 146 } else { 147 fillArea, padArea = output[maxFillLength:bufSize], output[0:maxFillLength] 148 output = output[inputLength+maxFillLength-padLength:] 149 } 150 151 // copy data 152 copy(fillArea, input) 153 // fill pad 154 FillByte(padArea, pad) 155 return 156 } 157 158 // BytesUnPadSingle method removes a given pad character from both ends. 159 func BytesUnPadSingle(input []byte, pad byte, rightPad bool, copyData bool) (output []byte) { 160 var ( 161 limit = len(input) 162 offset = 0 163 ) 164 if rightPad { 165 for ; limit > offset; limit-- { 166 if input[limit-1] != pad { 167 break 168 } 169 } 170 } else { 171 for ; offset < limit; offset++ { 172 if input[offset] != pad { 173 break 174 } 175 } 176 } 177 if limit-offset < 1 { 178 return 179 } 180 if copyData { 181 output = make([]byte, limit-offset) 182 copy(output, input[offset:limit]) 183 } else { 184 output = input[offset:limit] 185 } 186 return 187 }