英文:
Golang Read Bytes from net.TCPConn
问题
ioutil.ReadAll
函数没有直接提供一个能够在遇到EOF或读取到指定字节数(以先到者为准)时停止读取的版本。
但是,你可以使用io.LimitedReader
结构体来实现类似的功能。io.LimitedReader
接受一个io.Reader
接口和一个字节数作为参数,并将读取操作限制在指定的字节数内。
下面是一个示例代码,演示如何使用io.LimitedReader
来实现你所描述的功能:
package main
import (
"fmt"
"io"
"io/ioutil"
"strings"
)
func main() {
reader := strings.NewReader("This is a sample string.")
limit := 10 // 限制读取的字节数
lr := &io.LimitedReader{R: reader, N: int64(limit)}
data, err := ioutil.ReadAll(lr)
if err != nil {
fmt.Println("读取错误:", err)
return
}
fmt.Println(string(data))
}
在上面的示例中,我们使用strings.NewReader
创建了一个包含示例字符串的io.Reader
接口。然后,我们创建了一个io.LimitedReader
,将其作为参数传递给ioutil.ReadAll
函数。io.LimitedReader
将限制读取操作在指定的字节数内,即使还没有遇到EOF。
请注意,上述示例中的limit
变量可以根据你的需求进行调整,以指定你想要读取的字节数。
英文:
Is there a version of ioutil.ReadAll
that will read until it reaches an EOF OR if it reads n
bytes (whichever comes first)?
I cannot just take the first n
bytes from an ioutil.ReadAll
dump for DOS reasons.
答案1
得分: 3
你可以使用io.ReadFull、io.LimitedReader或者http.MaxBytesReader来实现你需要的功能。如果你需要不同的行为,可以先查看它们的实现方式,然后根据需要进行修改。
英文:
io.ReadFull
or
io.LimitedReader
or
http.MaxBytesReader.
If you need something different first look at how those are implemented, it'd be trivial to roll your own with tweaked behavior.
答案2
得分: 3
有几种方法可以实现您的要求,您可以选择其中一种。
func ReadFull(r Reader, buf []byte) (n int, err error)
> ReadFull 从 r 中精确地读取 len(buf) 个字节到 buf 中。它返回复制的字节数和一个错误,如果读取的字节数少于 len(buf)。只有在没有读取任何字节时,错误才是 EOF。
func LimitReader(r Reader, n int64) Reader
LimitReader 返回一个从 r 中读取,但在读取 n 个字节后停止并返回 EOF 的 Reader。底层实现是 *LimitedReader。
func CopyN(dst Writer, src Reader, n int64) (written int64, err error)
> CopyN 从 src 复制 n 个字节(或直到出现错误)到 dst。它返回复制的字节数和在复制过程中遇到的最早的错误。返回时,只有在 err == nil 时 written == n。
func ReadAtLeast(r Reader, buf []byte, min int) (n int, err error)
> ReadAtLeast 从 r 中读取到 buf 中,直到至少读取了 min 个字节。它返回复制的字节数和一个错误,如果读取的字节数少于 min。只有在没有读取任何字节时,错误才是 EOF。
英文:
There are a couple of ways to achieve your requirement. You can use either one.
func ReadFull(r Reader, buf []byte) (n int, err error)
> ReadFull reads exactly len(buf) bytes from r into buf. It returns the
> number of bytes copied and an error if fewer bytes were read. The
> error is EOF only if no bytes were read.
func LimitReader(r Reader, n int64) Reader
LimitReader returns a Reader that reads from r but stops with EOF after n bytes. The underlying implementation is a *LimitedReader.
func CopyN(dst Writer, src Reader, n int64) (written int64, err error)
> CopyN copies n bytes (or until an error) from src to dst. It returns
> the number of bytes copied and the earliest error encountered while
> copying. On return, written == n if and only if err == nil.
func ReadAtLeast(r Reader, buf []byte, min int) (n int, err error)
> ReadAtLeast reads from r into buf until it has read at least min
> bytes. It returns the number of bytes copied and an error if fewer
> bytes were read. The error is EOF only if no bytes were read.
答案3
得分: 2
有两个选项。如果n
是你想要读取的字节数,r
是连接。
选项1:
p := make([]byte, n)
_, err := io.ReadFull(r, p)
选项2:
p, err := io.ReadAll(&io.LimitedReader{R: r, N: n})
如果应用程序通常填充缓冲区,则第一种选项更高效。
如果你正在从HTTP请求体中读取数据,则使用http.MaxBytesReader。
英文:
There are two options. If n
is the number of bytes you want to read and r
is the connection.
Option 1:
p := make([]byte, n)
_, err := io.ReadFull(r, p)
Option 2:
p, err := io.ReadAll(&io.LimitedReader{R: r, N: n})
The first option is more efficient if the application typically fills the buffer.
If you are reading from an HTTP request body, then use http.MaxBytesReader.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论