unpacked.go (65 lines of code) (raw):

// Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved package qf import ( "encoding/binary" "fmt" "io" "os" ) type unpacked []uint64 var _ Vector = (*unpacked)(nil) // UnpackedVectorAllocate allocates non-bitpacked storage with a portable // serialization format (i.e. between architectures) func UnpackedVectorAllocate(bits uint, size uint64) Vector { if bits > bitsPerWord { panic(fmt.Sprintf("bit size of %d is greater than word size of %d, not supported", bits, bitsPerWord)) } arr := make(unpacked, size) return &arr } func (v *unpacked) Set(ix uint64, val uint64) { (*v)[ix] = val } func (v *unpacked) Swap(ix uint64, val uint64) (oldval uint64) { (*v)[ix], oldval = val, (*v)[ix] return } func (v *unpacked) Get(ix uint64) (val uint64) { return (*v)[ix] } // unpacked format on disk is: // 64 bit len // len x 64 bit unsigned integers func (v unpacked) WriteTo(w io.Writer) (n int64, err error) { return writeUintSlice(w, v) } func (v *unpacked) ReadFrom(r io.Reader) (n int64, err error) { *v, n, err = readUintSlice(r) return } type unpackedDiskReader struct { r io.ReaderAt start uint64 size uint64 } func initUnpackedDiskReader(rdr *os.File) (*unpackedDiskReader, error) { var sz uint64 err := binary.Read(rdr, binary.LittleEndian, &sz) if err != nil { return nil, err } cur, err := rdr.Seek(0, io.SeekCurrent) if err != nil { return nil, err } // seek to end _, err = rdr.Seek(cur+int64(8*sz), io.SeekStart) return &unpackedDiskReader{rdr, uint64(cur), uint64(sz)}, err } func (r unpackedDiskReader) Read(ix uint64) (val uint64, err error) { var data [8]byte off := int64(ix*8 + r.start) n, err := r.r.ReadAt(data[:8], off) if err != nil { return 0, err } if n != 8 { return 0, fmt.Errorf("short read: %d/8", n) } val = binary.LittleEndian.Uint64(data[:8]) return }