File io 来自[]字节或文件的io.WriteSeeker和io.ReadSeeker

File io 来自[]字节或文件的io.WriteSeeker和io.ReadSeeker,file-io,go,buffer,File Io,Go,Buffer,我有一种叫做“DoSomething”的方法。DoSomething将获取二进制源数据并对其执行操作,然后写出二进制数据。DoSomething需要足够通用,以处理源和目标的[]字节数组或文件句柄。为了实现这一点,我尝试如下声明方法: package main import ( "fmt" "io" "os" ) func main() { f, err := os.Open("test.txt") if err != nil { fmt.Printl

我有一种叫做“DoSomething”的方法。DoSomething将获取二进制源数据并对其执行操作,然后写出二进制数据。DoSomething需要足够通用,以处理源和目标的[]字节数组或文件句柄。为了实现这一点,我尝试如下声明方法:

package main

import (
   "fmt"
   "io"
   "os"
)

func main() {
   f, err := os.Open("test.txt")
   if err != nil {
     fmt.Println(err)
   }
   defer f.Close()
   f2, err := os.Create("test2.txt")
   if err != nil {
      fmt.Println(err)
   }
   defer f2.Close()
   DoSomething(f, f2) 
}

func DoSomething(source io.ReadSeeker, destination io.WriteSeeker) {
   io.Copy(destination, source)
}
destination := filebuffer.NewFileBuffer()

source, err := os.Open(pathString)
if err != nil {
    return nil, err
}
defer source.Close()

if _, err := encrypter.Decrypt(source, &destination, password); err != nil {
    return nil, err
}
func DoSomething(源*io.readseek,目标*io.writeseek)

我已经实现了ReadSeeker和WriteSeeker,用于使用缓冲区,使用了我自己定制的、必需的方法(如果有一种方法可以自动完成这项工作,我也很想听听)。
不幸的是,我似乎不知道如何从文件句柄创建io.readseek或io.writeseek。我相当肯定,一定有一些预先准备好的方法来处理这个问题,而不必手动实现它们。这可能吗?

一个文件已经实现了这两个功能。您可以这样做:

package main

import (
   "fmt"
   "io"
   "os"
)

func main() {
   f, err := os.Open("test.txt")
   if err != nil {
     fmt.Println(err)
   }
   defer f.Close()
   f2, err := os.Create("test2.txt")
   if err != nil {
      fmt.Println(err)
   }
   defer f2.Close()
   DoSomething(f, f2) 
}

func DoSomething(source io.ReadSeeker, destination io.WriteSeeker) {
   io.Copy(destination, source)
}
destination := filebuffer.NewFileBuffer()

source, err := os.Open(pathString)
if err != nil {
    return nil, err
}
defer source.Close()

if _, err := encrypter.Decrypt(source, &destination, password); err != nil {
    return nil, err
}

另外,您不需要向接口传递指针,这使得处理接口更容易。

对于其他需要完成类似任务的人,我的结论如下。它还不完整,但距离我所需要的足够近:

package filebuffer

import (
    "bytes"
    "errors"
)

type FileBuffer struct {
    Buffer bytes.Buffer
    Index  int64
}

func NewFileBuffer() FileBuffer {
    return FileBuffer{}
}

func (fbuffer *FileBuffer) Bytes() []byte {
    return fbuffer.Buffer.Bytes()
}

func (fbuffer *FileBuffer) Read(p []byte) (int, error) {
    n, err := bytes.NewBuffer(fbuffer.Buffer.Bytes()[fbuffer.Index:]).Read(p)

    if err == nil {
        if fbuffer.Index+int64(len(p)) < int64(fbuffer.Buffer.Len()) {
            fbuffer.Index += int64(len(p))
        } else {
            fbuffer.Index = int64(fbuffer.Buffer.Len())
        }
    }

    return n, err
}

func (fbuffer *FileBuffer) Write(p []byte) (int, error) {
    n, err := fbuffer.Buffer.Write(p)

    if err == nil {
        fbuffer.Index = int64(fbuffer.Buffer.Len())
    }

    return n, err
}

func (fbuffer *FileBuffer) Seek(offset int64, whence int) (int64, error) {
    var err error
    var Index int64 = 0

    switch whence {
    case 0:
        if offset >= int64(fbuffer.Buffer.Len()) || offset < 0 {
            err = errors.New("Invalid Offset.")
        } else {
            fbuffer.Index = offset
            Index = offset
        }
    default:
        err = errors.New("Unsupported Seek Method.")
    }

    return Index, err
}

谢谢这应该是显而易见的。我可以从[]字节缓冲区创建一个ReadSeeker/WriteSeeker,而不用手动实现所有方法吗?我原以为
bytes.buffer
包可以处理它,但显然不行。在google组中搜索关于seeker和bytes的帖子。所以,是的,如果你真的需要的话,你可能需要将它包装在实现
Seek
的东西中。我写了一个包,它正好满足你的需要。新结构由
字节缓冲区支持,并实现
io.Reader
io.Seeker
io.ReaderAt
io.Writer
等。。pkg的主要目的是避免在数据不需要持久化时使用文件(临时或非临时)。这是包裹: