Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Let's consider two solutions.</p> <h1>Base 32</h1> <p>For fun, let's consider using base-32 numbers. Yes, you can do that in JavaScript.</p> <p>First pack four 7-bit values into one integer:</p> <pre><code>function pack(a1,a2,a3,a4){ return ((a1 &lt;&lt; 8 | a2) &lt;&lt; 8 | a3) &lt;&lt; 8 | a4; } </code></pre> <p>Now, convert to base 32.</p> <pre><code>function encode(n){ var str = "000000" + n.toString(32); str = str.slice(0,6); return str; } </code></pre> <p>That should be not more than six digits. We make sure it's exactly six.</p> <p>Going the other direction:</p> <pre><code>function decode(s){ return parseInt(s, 32); } function unpack(x){ var a1 = x &amp; 0xff0000&gt;&gt;24, a2 = x &amp; 0x00ff0000&gt;&gt;16, a3 = x &amp; 0x0000ff00&gt;&gt;8, a4 = x &amp; 0x000000ff; return [a1, a2, a3, a4]; } </code></pre> <p>All that remains is to wrap the logic around this to handle the 6000 elements. To compress:</p> <pre><code>function compress(elts){ var str = ''; for(var i = 0; i &lt; elts.length; i+=4){ str += encode(pack(elts[i], elts[i+1], elts[i+2], elts[i+3]) } return str; } </code></pre> <p>And to uncompress:</p> <pre><code>function uncompress(str){ var elts = []; for(var i = 0; i &lt; str.length; i+=6){ elts = elts.concat(unpack(decode(str.slice(i, i+6))); } return elts; } </code></pre> <p>If you concatenate the results for all 6,000 elements, you'll have 1,500 packed numbers, which at six characters each will turn into about 9K. It's about 1.5 bytes per 7-bit value. It's by no means the information-theoretic maximum compression, but it's not that bad. To decode simply reverse the process:</p> <h1>Unicode</h1> <p>First we'll pack two 7-bit values into one integer:</p> <pre><code>function pack(a1,a2){ return (a1 &lt;&lt; 8 | a2) &lt;&lt; 8; } </code></pre> <p>We'll do this for all 6,000 inputs, then use our friend <code>String.fromCharCode</code> to turn all 3,000 values into a 3,000-character Unicode string:</p> <pre><code>function compress(elts){ var packeds = []; for (var i = 0; i &lt; elts.length; i+=2) { packeds.push(pack(elts[i], elts[i+1]); } return String.fromCharCode.apply(0, packeds); } </code></pre> <p>Coming back the other way, it's quite easy:</p> <pre><code>function uncompress(str) { var elts = [], code; for (var i = 0; i &lt; str.length; i++) { code=str.charCodeAt(i); elts.push(code&gt;&gt;8, code &amp; 0xff); } return elts; } </code></pre> <p>This will take up two bytes per two 7-bit values, so about 33% more efficient than the base 32 approach.</p> <p>If the above string is going to be written out into a script tag as a Javascript assignment such as <code>var data="HUGE UNICODE STRING";</code>, then quotation marks in string will need to be escaped:</p> <pre><code>javascript_assignment = 'var data = "' + compress(elts).replace(/"/g,'\\"') + '";'; </code></pre> <p>The above code is not meant to be production, and in particular does not handle edge cases where the the number of inputs is not a multiple of four or two.</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload