提问人:user892960 提问时间:2/16/2023 更新时间:2/16/2023 访问量:232
转换自 'bufio.Reader“改为”io.ReadWriteCloser'
convert from `bufio.Reader` to `io.ReadWriteCloser`
问:
我有一个我想在不推进读者的情况下窥视它,io.ReadWriteCloser
所以我正在使用
bi := bufio.NewReader(i)
bi.Peek(1)
到目前为止一切顺利,但是后来当我想重用原始()时,它只有.io.ReadWriteCloser
i
EOF
所以我的问题是如何从 back 转换回bufio.Reader
io.ReadWriteCloser
答:
0赞
Sam Herrmann
2/16/2023
#1
正如我在上面的评论中提到的,您需要访问原始读者的方法。这意味着将读者作为 an 传递是不够的。话虽如此,以下帮助程序函数可能是一种解决方法:Seek
io.ReadWriteCloser
func peek(r io.Reader, n int) ([]byte, error) {
bi := bufio.NewReader(r)
peeked, err := bi.Peek(n)
if err != nil {
return nil, err
}
// Use type assertion to check if r implements the
// io.Seeker interface. If it does, then use it to
// reset the offset.
if seeker, ok := r.(io.Seeker); ok {
seeker.Seek(0, 0)
}
return peeked, nil
}
现在你可以把 传递给这个函数。该函数检查读取器是否碰巧实现了该方法。如果该方法已实现,则将调用它。io.ReadWriteCloser
peek
peek
Seek
Seek
peek
评论
0赞
user892960
2/17/2023
另一个被接受的答案解决了我的问题,而无需调用io.Seeker.Seek()
3赞
Penny Stevens
2/16/2023
#2
因为 bufio.读取器缓冲来自底层读取器的数据,应用程序必须从 bufio 读取数据。调用 Peek 后的读者。
要获取 io。执行此操作的 ReadWriteCloser 包装 bufio。Reader 和原始 io。ReadWriteCloser:
// BufferedReadWriteCloser has all of the methods
// from *bufio.Reader and io.ReadWriteCloser.
type BufferedReadWriteCloser struct {
*bufio.Reader
io.ReadWriteCloser
}
func (rw *BufferedReadWriteCloser) Read(p []byte) (int, error) {
return rw.Reader.Read(p)
}
以下是如何使用它:
rw := &BufferedReadWriteCloser{bufio.NewReader(i), i}
p, err := rw.Peek(1)
的值满足 io。ReadWriteCloser 接口。rw
没有要求或假设 io.ReadWriteCloser 具有 Seek 方法。
评论
0赞
user892960
2/16/2023
简洁的解决方案!创建两种类型的混合体,以便接口满足,而最重要的接口现在被“重定向”到io.ReadWriteCloser
Read()
bufio.Reader.Read()
评论
i.Seek(0, 0)
bi.Peek(1)
io.ReadWriteCloser
io.ReadWriteSeeker
io.ReadWriteCloser
Seek
io.ReadWriteCloser
Peek()
io.ReadWriteCloser
Peek()
Seek()/Peak()