摘要:笔者在编码详解与中编码实践一文中介绍了中编码相关的基础知识,其中没有介绍纯粹的编解码方案,笔者后来根据网上的代码完善了下这个库,并且对中三种不同的编解码方案进行了比较。
Isomorphic Urlencode
Here is English Version For README
笔者在URL编码详解与DOM中GBK编码实践一文中介绍了JavaScript中URL编码相关的基础知识,其中没有介绍纯粹的JavaScript编解码方案,笔者后来根据网上的代码完善了下Isomorphic Urlencode这个库,并且对JavaScript中三种不同的编解码方案进行了比较。核心的出发点为
对于浏览器中版本使用纯粹的前端代码实现GBK编码
保证能够在Node与Browser环境下实现无缝对切
可以使用npm命令直接安装该依赖:
npm install --save isomorphic-urlencodeUsage Pure JavaScript
基于纯粹的JavaScript优势在于可以跨平台使用,不过缺陷在于其性能相对较差,另外目前只支持GBK/GB2312编码,不如另外两种可以用于其他编码规范。在使用纯粹的JavaScript中,如果使用UTF8编码,那么直接调用JavaScript内置的encodeURIComponent,如果使用GBK编码,那么会使用如下两个函数,其关键代码为:
function gbkEncode(str) { return str.replace(/./g, function (a) { var code = a.charCodeAt(0); if (isAscii(code)) { return encodeURIComponent(a); } else { var key = code.toString(16); if (key.length != 4)key = ("000" + key).match(/....$/)[0]; return U2Ghash[key] || a; } }); } function gbkDecode(str, callback) { return str.replace(/%[0-9A-F]{2}%[0-9A-F]{2}/g, function (a) { if (a in G2Uhash) { return String.fromCharCode("0x" + G2Uhash[a]); } else { return a; } }).replace(/%[w]{2}/g, function (a) { return decodeURIComponent(a); }); }Node
Node版本使用了 node-urlencode,其对于UTF8的编解码也是使用了JavaScript内置的encodeURIComponent,而对于GBK等其他编码使用了iconv-lite这个库:
function encode(str, charset) { if (isUTF8(charset)) { return encodeURIComponent(str); } var buf = iconv.encode(str, charset); var encodeStr = ""; var ch = ""; for (var i = 0; i < buf.length; i++) { ch = buf[i].toString("16"); if (ch.length === 1) { ch = "0" + ch; } encodeStr += "%" + ch; } encodeStr = encodeStr.toUpperCase(); return encodeStr; }DOM
如果你是在浏览器环境中使用,请在HTML文件头部添加:
if (parent._urlEncode_iframe_callback) { parent._urlEncode_iframe_callback(location.search.split("=")[1]); //直接关闭当前子窗口 window.close(); }
注意,上面一段代码是将自身作为iframe的加载地址,因此务必放在HTML文件首部。然后在JS代码中使用:
var urlencode = require("isomorphic-urlencode").dom; urlencode("王下邀月熊").then(function (data) { console.log(data); //测试解码 urlencode.decode(data).then(function (data) { console.log(data); }) }); urlencode("王下邀月熊", "gbk").then(function (data) { console.log(data); //测试解码 urlencode.decode(data, "gbk").then(function (data) { console.log(data); }) });
浏览器版本主要基于iframe与form实现,详细原理参考这篇博客
Benchmark Pure JavaScript VS DOM主要的测试代码如下所示,从结果中可见对于大数据串还是使用DOM效率较好,但是基于DOM的解决方案需要嵌入iframe,这个可能造成额外的代码侵入与性能损耗。
/** * Created by apple on 16/9/8. */ var urlencode = require("../urlencode"); var urlencodeDOM = require("../urlencode").dom; //测试长字符串编码时间 var str = ""; for (i = 0; i < 100000; i++) { str += "王下邀月熊"; } console.time("基于Pure JavaScript的编解码"); urlencode.decode(urlencode(str, "gbk"), "gbk"); console.timeEnd("基于Pure JavaScript的编解码"); console.time("基于DOM的编解码"); urlencodeDOM(str, "gbk").then(function (data) { //测试解码 urlencodeDOM.decode(data, "gbk").then(function (data) { console.timeEnd("基于DOM的编解码") }) }); //测试短时间内多次编码 var timerPure = 0; var timerDOM = 0; str = "王下邀月熊"; for (i = 0; i < 1000; i++) { var start = new Date(); urlencode.decode(urlencode(str, "gbk"), "gbk"); timerPure += new Date().getMilliseconds() - start.getMilliseconds(); (function test(start) { urlencodeDOM(str, "gbk").then(function (data) { //测试解码 urlencodeDOM.decode(data, "gbk").then(function (data) { timerDOM += new Date().getMilliseconds() - start.getMilliseconds(); console.log("timerDOM:" + timerDOM); }) }); })(new Date()); } console.log("timerPure:" + timerPure); // 基于Pure JavaScript的编解码: 526.27ms // 基于DOM的编解码: 155.32msPure JavaScript VS Node
主要的测试代码如下所示,可以看出基于Node的编解码速度会快于纯粹的JavaScript编解码。
/** * Created by apple on 16/9/8. */ var urlencode = require("./urlencode"); var urlencodeNode = require("./node-urlencode"); //测试长字符串编码时间 var str = ""; for (i = 0; i < 1000000; i++) { str += "王下邀月熊"; } console.time("基于Pure JavaScript的编解码"); urlencode.decode(urlencode(str)); urlencode.decode(urlencode(str, "gbk"), "gbk"); console.timeEnd("基于Pure JavaScript的编解码"); console.time("基于NODE的编解码"); urlencodeNode.decode(urlencode(str)); urlencodeNode.decode(urlencode(str, "gbk"), "gbk"); console.timeEnd("基于NODE的编解码"); // 基于Pure JavaScript的编解码: 526.27ms // 基于DOM的编解码: 155.32ms //测试短时间内多次编码 var timerPure = 0; var timerNODE = 0; str = "王下邀月熊王下邀月熊王下邀月熊王下邀月熊"; for (i = 0; i < 1000; i++) { var start = new Date(); urlencode.decode(urlencode(str)); urlencode.decode(urlencode(str, "gbk"), "gbk"); timerPure += new Date().getMilliseconds() - start.getMilliseconds(); } for (i = 0; i < 1000; i++) { var start = new Date(); urlencodeNode.decode(urlencode(str)); urlencodeNode.decode(urlencode(str, "gbk"), "gbk"); timerNODE += new Date().getMilliseconds() - start.getMilliseconds(); } console.log("timerPure:" + timerPure); console.log("timerNODE:" + timerNODE); // 基于Pure JavaScript的编解码: 10932.610ms // 基于NODE的编解码: 7585.223ms // timerPure:28 // timerNODE:31Test
使用node node-urlencode.test.js来测试Node环境下转码。
使用webpack demo/demo.js demo/demo.dist.js,然后在浏览器中打开demo.html,在Console中可以查看运行结果
文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。
转载请注明本文地址:https://www.ucloud.cn/yun/80360.html
摘要:,,等属于不同的字符集,转换编码就是在它们中的任意两者间进行。一般个人用的电脑上控制台基本上都是编码的,但运维的机器上基本全是,中文的时候就会有酸爽的问题。 总结总结,本文仅适用于python2.x 默认编码与开头声明 首先是开头的地方声明编码 # coding: utf8 这个东西的用处是声明文件编码为utf8(要写在前两行内),不然文件里如果有中文,比如 a = 美丽 b = u美...
摘要:只有彻底理解编码,遇到编码问题才知道问题的根源在哪里,并找到对应的解决办法。花一点时间去彻底消化并理解他,长远来看,对以后工作效率的提升是非常值得的。比如中国就制定了等编码规范。 只要涉及编程工作,编码是永远绕不开的问题。只有彻底理解编码,遇到编码问题才知道问题的根源在哪里,并找到对应的解决办法。花一点时间去彻底消化并理解他,长远来看,对以后工作效率的提升是非常值得的。下面是我对编码的...
阅读 3640·2021-10-13 09:40
阅读 3118·2021-10-09 09:53
阅读 3529·2021-09-26 09:46
阅读 1811·2021-09-08 09:36
阅读 4218·2021-09-02 09:46
阅读 1293·2019-08-30 15:54
阅读 3050·2019-08-30 15:44
阅读 1005·2019-08-30 11:06