技术实践
JavaScript对数据压缩和解压
当文本达到一定长度,且内容中重复的字符出现次数较多,就可以有一个不错的压缩率。通过js实现压缩,发送到后端再实现解压。有效提升同等网络带宽下

当文本达到一定长度,且内容中重复的字符出现次数较多,就可以有一个不错的压缩率。通过js实现压缩,发送到后端再实现解压。有效提升同等网络带宽下的传输速率
最近遇到一个项目,传输后端的数据非常大,于是考虑到压缩在进行传输,本次讲解只在客户端压缩
封装压缩和解压缩方法
以下方法来自网络搜索,频率出现高的
压缩
js
function Compress(strNormalString) {
var strCompressedString = "";
var ht = new Array();
for(i = 0; i < 128; i++) {
ht[i] = i;
}
var used = 128;
var intLeftOver = 0;
var intOutputCode = 0;
var pcode = 0;
var ccode = 0;
var k = 0;
for(var i=0; i<strNormalString.length; i++) {
ccode = strNormalString.charCodeAt(i);
k = (pcode << 8) | ccode;
if(ht[k] != null) {
pcode = ht[k];
} else {
intLeftOver += 12;
intOutputCode <<= 12;
intOutputCode |= pcode;
pcode = ccode;
if(intLeftOver >= 16) {
strCompressedString += String.fromCharCode( intOutputCode >> ( intLeftOver - 16 ) );
intOutputCode &= (Math.pow(2, (intLeftOver - 16)) - 1);
intLeftOver -= 16;
}
if(used < 4096) {
used ++;
ht[k] = used - 1;
}
}
}
if(pcode != 0) {
intLeftOver += 12;
intOutputCode <<= 12;
intOutputCode |= pcode;
}
if(intLeftOver >= 16) {
strCompressedString += String.fromCharCode( intOutputCode >> ( intLeftOver - 16 ) );
intOutputCode &= (Math.pow(2,(intLeftOver - 16)) - 1);
intLeftOver -= 16;
}
if( intLeftOver > 0) {
intOutputCode <<= (16 - intLeftOver);
strCompressedString += String.fromCharCode( intOutputCode );
}
return strCompressedString;
}
解压
js
function Decompress(strCompressedString) {
var strNormalString = "";
var ht = new Array();
for(i = 0; i < 128; i++) {
ht[i] = String.fromCharCode(i);
}
var used = 128;
var intLeftOver = 0;
var intOutputCode = 0;
var ccode = 0;
var pcode = 0;
var key = 0;
for(var i=0; i<strCompressedString.length; i++) {
intLeftOver += 16;
intOutputCode <<= 16;
intOutputCode |= strCompressedString.charCodeAt(i);
while(1) {
if(intLeftOver >= 12) {
ccode = intOutputCode >> (intLeftOver - 12);
if( typeof( key = ht[ccode] ) != "undefined" ) {
strNormalString += key;
if(used > 128) {
ht[ht.length] = ht[pcode] + key.substr(0, 1);
}
pcode = ccode;
} else {
key = ht[pcode] + ht[pcode].substr(0, 1);
strNormalString += key;
ht[ht.length] = ht[pcode] + key.substr(0, 1);
pcode = ht.length - 1;
}
used ++;
intLeftOver -= 12;
intOutputCode &= (Math.pow(2,intLeftOver) - 1);
} else {
break;
}
}
}
return strNormalString;
}
使用Pako.js插件
引入CDN
html
<script src="https://cdn.staticfile.org/pako/1.0.10/pako.min.js"></script>
NPM
js
npm install pako
GitHub
https://github.com/nodeca/pako
使用
定义解压和压缩的方法
js
function unzip(b64Data){
var strData = atob(b64Data);
// Convert binary string to character-number array
var charData = strData.split('').map(function(x){return x.charCodeAt(0);});
// Turn number array into byte-array
var binData = new Uint8Array(charData);
// // unzip
var data = pako.inflate(binData);
// Convert gunzipped byteArray back to ascii string:
strData = String.fromCharCode.apply(null, new Uint16Array(data));
return decodeURIComponent(strData);
}
function zip(str){
var binaryString = pako.gzip(encodeURIComponent(str), { to: 'string' })
return btoa(binaryString);
}
效果,字符串越大,压缩效果越明显
