@@ -1,58 +1,44 @@ package main import ( + fib "0dev.org/encoding/fibonacci" mtf "0dev.org/encoding/mtf" iou "0dev.org/ioutil" "flag" - "fmt" "io" "os" ) func main() { - d := flag.Bool("d", false, "Use to toggle decode mode") - flag.Parse() - - var code int - if *d { - code = decode(os.Stdout, os.Stdin) - } else { - code = encode(os.Stdout, os.Stdin) - } - - os.Exit(code) -} - -// Transforms the data according to the move-to-front algorithm -// I/O is buffered for better performance -func encode(output io.Writer, input io.Reader) int { - var ( - err error - encoder io.Reader = mtf.Encoder(iou.SizedReader(input, 4096)) - ) - - _, err = io.Copy(output, encoder) - if err != nil { - fmt.Fprintln(os.Stderr, "Error while encoding.\n", err) - return 1 - } - - return 0 -} - -// Reverses MTF`ed data and writes back the original bytes -// I/O is buffered for better performance -func decode(output io.Writer, input io.Reader) int { - var ( - err error - decoder io.Reader = mtf.Decoder(iou.SizedReader(input, 4096)) - ) - - _, err = io.Copy(output, decoder) - if err != nil { - fmt.Fprintln(os.Stderr, "Error while decoding.\n", err) - return 1 - } - - return 0 + d := flag.Bool("d", false, "Toggle decode mode.") + flag.Parse() + + var ( + input io.Reader = iou.SizedReader(os.Stdin, 4096) + output io.Writer = iou.SizedWriter(os.Stdout, 4096) + code int + ) + + // Exit handler + defer func() { + os.Exit(code) + }() + + // Flush the output buffer + defer output.Write(nil) + + if *d { + input = mtf.Decoder(fib.Decoder(input)) + } else { + input = mtf.Encoder(input) + + // Encode output as fibonacci integers + output = fib.Encoder(output) + defer output.Write(nil) + } + + if _, err := io.Copy(output, input); err != nil { + os.Stderr.WriteString("Error while transforming data.\n" + err.Error()) + code = 1 + } }