gitee.com/quant1x/gox@v1.21.2/encoding/binary/struc/README.md (about)

     1  [![Build Status](https://travis-ci.org/lunixbochs/struc.svg?branch=master)](https://travis-ci.org/lunixbochs/struc) [![GoDoc](https://godoc.org/github.com/lunixbochs/struc?status.svg)](https://godoc.org/github.com/lunixbochs/struc)
     2  
     3  struc
     4  ====
     5  
     6  Struc exists to pack and unpack C-style structures from bytes, which is useful for binary files and network protocols. It could be considered an alternative to `encoding/binary`, which requires massive boilerplate for some similar operations.
     7  
     8  Take a look at an [example comparing `struc` and `encoding/binary`](https://bochs.info/p/cxvm9)
     9  
    10  Struc considers usability first. That said, it does cache reflection data and aims to be competitive with `encoding/binary` struct packing in every way, including performance.
    11  
    12  Example struct
    13  ----
    14  
    15  ```Go
    16  type Example struct {
    17      Var   int `struc:"int32,sizeof=Str"`
    18      Str   string
    19      Weird []byte `struc:"[8]int64"`
    20      Var   []int `struc:"[]int32,little"`
    21  }
    22  ```
    23  
    24  Struct tag format
    25  ----
    26  
    27   - ```Var []int `struc:"[]int32,little,sizeof=StringField"` ``` will pack Var as a slice of little-endian int32, and link it as the size of `StringField`.
    28   - `sizeof=`: Indicates this field is a number used to track the length of a another field. `sizeof` fields are automatically updated on `Pack()` based on the current length of the tracked field, and are used to size the target field during `Unpack()`.
    29   - Bare values will be parsed as type and endianness.
    30  
    31  Endian formats
    32  ----
    33  
    34   - `big` (default)
    35   - `little`
    36  
    37  Recognized types
    38  ----
    39  
    40   - `pad` - this type ignores field contents and is backed by a `[length]byte` containing nulls
    41   - `bool`
    42   - `byte`
    43   - `int8`, `uint8`
    44   - `int16`, `uint16`
    45   - `int32`, `uint32`
    46   - `int64`, `uint64`
    47   - `float32`
    48   - `float64`
    49  
    50  Types can be indicated as arrays/slices using `[]` syntax. Example: `[]int64`, `[8]int32`.
    51  
    52  Bare slice types (those with no `[size]`) must have a linked `Sizeof` field.
    53  
    54  Private fields are ignored when packing and unpacking.
    55  
    56  Example code
    57  ----
    58  
    59  ```Go
    60  package main
    61  
    62  import (
    63      "bytes"
    64      "github.com/lunixbochs/struc"
    65  )
    66  
    67  type Example struct {
    68      A int `struc:"big"`
    69  
    70      // B will be encoded/decoded as a 16-bit int (a "short")
    71      // but is stored as a native int in the struct
    72      B int `struc:"int16"`
    73  
    74      // the sizeof key links a buffer's size to any int field
    75      Size int `struc:"int8,little,sizeof=Str"`
    76      Str  string
    77  
    78      // you can get freaky if you want
    79      Str2 string `struc:"[5]int64"`
    80  }
    81  
    82  func main() {
    83      var buf bytes.Buffer
    84      t := &Example{1, 2, 0, "test", "test2"}
    85      err := struc.Pack(&buf, t)
    86      o := &Example{}
    87      err = struc.Unpack(&buf, o)
    88  }
    89  ```
    90  
    91  Benchmark
    92  ----
    93  
    94  `BenchmarkEncode` uses struc. `Stdlib` benchmarks use equivalent `encoding/binary` code. `Manual` encodes without any reflection, and should be considered an upper bound on performance (which generated code based on struc definitions should be able to achieve).
    95  
    96  ```
    97  BenchmarkEncode        1000000   1265 ns/op
    98  BenchmarkStdlibEncode  1000000   1855 ns/op
    99  BenchmarkManualEncode  5000000    284 ns/op
   100  BenchmarkDecode        1000000   1259 ns/op
   101  BenchmarkStdlibDecode  1000000   1656 ns/op
   102  BenchmarkManualDecode  20000000  89.0 ns/op
   103  ```