Go语言根据字符串长度动态调整ASCII编码缓冲区大小的实现方法
首先纠正一个用法误区:你引入的encoding/ascii85是实现Ascii85(Base85)二进制编码的工具包,和你要实现的C# ASCIIEncoding.GetBytes功能完全不同。C#对应方法的作用是将字符串中的每个字符转换为对应的ASCII单字节值,非ASCII范围的字符会被替换为?,这个需求在Go中不需要引入额外编码包就能实现。
1. 和C#功能完全对齐的实现
你不需要硬编码缓冲区长度,直接根据输入字符串长度初始化缓冲区即可:
func StrToByteArray(str string) []byte { // 每个字符最终对应1个字节,初始容量设为字符串长度避免扩容 res := make([]byte, 0, len(str)) for _, r := range str { if r < 0x80 { // 属于ASCII范围 res = append(res, byte(r)) } else { // 非ASCII替换为? 和C#行为一致 res = append(res, '?') } } return res }
2. 如果你确实需要使用Ascii85编码,动态计算缓冲区长度的方法
Ascii85编码的规则是每4字节原始数据编码为5字节结果,标准库已经提供了计算最大长度的方法:
- 编码缓冲区最大长度用
ascii85.MaxEncodedLen(原始数据长度)计算 - 解码缓冲区最大长度可以直接用
编码后长度 * 4 / 5计算
修改后的代码如下:
import ( "encoding/ascii85" "fmt" ) func main() { input := []byte("Hello, playground") // 动态分配编码缓冲区 encodeDst := make([]byte, ascii85.MaxEncodedLen(len(input))) // 获取实际编码写入的字节数 encodeLen := ascii85.Encode(encodeDst, input) // 截断到实际长度,避免输出多余的空字节 encodeDst = encodeDst[:encodeLen] fmt.Println(encodeDst) // 动态分配解码缓冲区 decodeDst := make([]byte, len(encodeDst)*4/5) // 获取实际解码写入的字节数 decodeLen, _, err := ascii85.Decode(decodeDst, encodeDst, false) if err != nil { panic(err) } decodeDst = decodeDst[:decodeLen] fmt.Println(string(decodeDst)) }
内容的提问来源于stack exchange,提问作者Blankman
相关产品推荐
相关产品推荐

