source: trip-planner-front/node_modules/hdr-histogram-js/src/ZigZagEncoding.ts@ 1ad8e64

Last change on this file since 1ad8e64 was 6a3a178, checked in by Ema <ema_spirova@…>, 3 years ago

initial commit

  • Property mode set to 100644
File size: 4.7 KB
RevLine 
[6a3a178]1/*
2 * This is a TypeScript port of the original Java version, which was written by
3 * Gil Tene as described in
4 * https://github.com/HdrHistogram/HdrHistogram
5 * and released to the public domain, as explained at
6 * http://creativecommons.org/publicdomain/zero/1.0/
7 */
8import ByteBuffer from "./ByteBuffer";
9
10const { pow, floor } = Math;
11
12const TWO_POW_7 = pow(2, 7);
13const TWO_POW_14 = pow(2, 14);
14const TWO_POW_21 = pow(2, 21);
15const TWO_POW_28 = pow(2, 28);
16const TWO_POW_35 = pow(2, 35);
17const TWO_POW_42 = pow(2, 42);
18const TWO_POW_49 = pow(2, 49);
19const TWO_POW_56 = pow(2, 56);
20
21/**
22 * This class provides encoding and decoding methods for writing and reading
23 * ZigZag-encoded LEB128-64b9B-variant (Little Endian Base 128) values to/from a
24 * {@link ByteBuffer}. LEB128's variable length encoding provides for using a
25 * smaller nuber of bytes for smaller values, and the use of ZigZag encoding
26 * allows small (closer to zero) negative values to use fewer bytes. Details
27 * on both LEB128 and ZigZag can be readily found elsewhere.
28 *
29 * The LEB128-64b9B-variant encoding used here diverges from the "original"
30 * LEB128 as it extends to 64 bit values: In the original LEB128, a 64 bit
31 * value can take up to 10 bytes in the stream, where this variant's encoding
32 * of a 64 bit values will max out at 9 bytes.
33 *
34 * As such, this encoder/decoder should NOT be used for encoding or decoding
35 * "standard" LEB128 formats (e.g. Google Protocol Buffers).
36 */
37class ZigZagEncoding {
38 /**
39 * Writes a long value to the given buffer in LEB128 ZigZag encoded format
40 * (negative numbers not supported)
41 * @param buffer the buffer to write to
42 * @param value the value to write to the buffer
43 */
44 static encode(buffer: ByteBuffer, value: number) {
45 if (value >= 0) {
46 value = value * 2;
47 } else {
48 value = -value * 2 - 1;
49 }
50
51 if (value < TWO_POW_7) {
52 buffer.put(value);
53 } else {
54 buffer.put(value | 0x80);
55 if (value < TWO_POW_14) {
56 buffer.put(floor(value / TWO_POW_7));
57 } else {
58 buffer.put(floor(value / TWO_POW_7) | 0x80);
59 if (value < TWO_POW_21) {
60 buffer.put(floor(value / TWO_POW_14));
61 } else {
62 buffer.put(floor(value / TWO_POW_14) | 0x80);
63 if (value < TWO_POW_28) {
64 buffer.put(floor(value / TWO_POW_21));
65 } else {
66 buffer.put(floor(value / TWO_POW_21) | 0x80);
67 if (value < TWO_POW_35) {
68 buffer.put(floor(value / TWO_POW_28));
69 } else {
70 buffer.put(floor(value / TWO_POW_28) | 0x80);
71 if (value < TWO_POW_42) {
72 buffer.put(floor(value / TWO_POW_35));
73 } else {
74 buffer.put(floor(value / TWO_POW_35) | 0x80);
75 if (value < TWO_POW_49) {
76 buffer.put(floor(value / TWO_POW_42));
77 } else {
78 buffer.put(floor(value / TWO_POW_42) | 0x80);
79 if (value < TWO_POW_56) {
80 buffer.put(floor(value / TWO_POW_49));
81 } else {
82 // should not happen
83 buffer.put(floor(value / TWO_POW_49) + 0x80);
84 buffer.put(floor(value / TWO_POW_56));
85 }
86 }
87 }
88 }
89 }
90 }
91 }
92 }
93 }
94
95 /**
96 * Read an LEB128-64b9B ZigZag encoded long value from the given buffer
97 * (negative numbers not supported)
98 * @param buffer the buffer to read from
99 * @return the value read from the buffer
100 */
101 static decode(buffer: ByteBuffer): number {
102 let v = buffer.get();
103 let value = v & 0x7f;
104 if ((v & 0x80) != 0) {
105 v = buffer.get();
106 value += (v & 0x7f) * TWO_POW_7;
107 if ((v & 0x80) != 0) {
108 v = buffer.get();
109 value += (v & 0x7f) * TWO_POW_14;
110 if ((v & 0x80) != 0) {
111 v = buffer.get();
112 value += (v & 0x7f) * TWO_POW_21;
113 if ((v & 0x80) != 0) {
114 v = buffer.get();
115 value += (v & 0x7f) * TWO_POW_28;
116 if ((v & 0x80) != 0) {
117 v = buffer.get();
118 value += (v & 0x7f) * TWO_POW_35;
119 if ((v & 0x80) != 0) {
120 v = buffer.get();
121 value += (v & 0x7f) * TWO_POW_42;
122 if ((v & 0x80) != 0) {
123 v = buffer.get();
124 value += (v & 0x7f) * TWO_POW_49;
125 if ((v & 0x80) != 0) {
126 v = buffer.get();
127 value += (v & 0x7f) * TWO_POW_56;
128 }
129 }
130 }
131 }
132 }
133 }
134 }
135 }
136 if (value % 2 === 0) {
137 value = value / 2;
138 } else {
139 value = -(value + 1) / 2;
140 }
141
142 return value;
143 }
144}
145
146export default ZigZagEncoding;
Note: See TracBrowser for help on using the repository browser.