JavaScript中实现sprintf、printf函数


Posted in Javascript onJanuary 27, 2015

在 JavaScript 下实现大多数语言中都有的 sprintf / printf 函数功能。

http://www.webtoolkit.info/javascript-sprintf.html : 比较完整的模拟sprintf函数功能。可用的格式化通配符:
1.%% - 返回百分号本身
2.%b - 二进制数字
3.%c - ASCII对应的字符
4.%d - 整数
5.%f - 浮点数
6.%o - 八进制数字
7.%s - 字符串
8.%x - 16进制数字 (小写字母形式)
9.%X - 16进制数字 (大写字母形式)

在 % 号和通配字符之间可用的选项包括 (比如 %.2f):

1.+      (强制在数字前面显示 + 和 - 符号作为正负数标记。缺省情况下只有负数才显示 - 符号)
2.-      (变量左对齐)
3.0      (使用0作为右对齐的填充字符)
4.[0-9]  (设置变量的最小宽度)
5..[0-9] (设置浮点数精度或字符串的长度)

/**

*

*  Javascript sprintf

*  http://www.webtoolkit.info/

*

*

**/
sprintfWrapper = {
  init : function () {
    if (typeof arguments == "undefined") { return null; }

    if (arguments.length < 1) { return null; }

    if (typeof arguments[0] != "string") { return null; }

    if (typeof RegExp == "undefined") { return null; }
    var string = arguments[0];

    var exp = new RegExp(/(%([%]|(\-)?(\+|\x20)?(0)?(\d+)?(\.(\d)?)?([bcdfosxX])))/g);

    var matches = new Array();

    var strings = new Array();

    var convCount = 0;

    var stringPosStart = 0;

    var stringPosEnd = 0;

    var matchPosEnd = 0;

    var newString = '';

    var match = null;
    while (match = exp.exec(string)) {

      if (match[9]) { convCount += 1; }
      stringPosStart = matchPosEnd;

      stringPosEnd = exp.lastIndex - match[0].length;

      strings[strings.length] = string.substring(stringPosStart, stringPosEnd);
      matchPosEnd = exp.lastIndex;

      matches[matches.length] = {

        match: match[0],

        left: match[3] ? true : false,

        sign: match[4] || '',

        pad: match[5] || ' ',

        min: match[6] || 0,

        precision: match[8],

        code: match[9] || '%',

        negative: parseInt(arguments[convCount]) < 0 ? true : false,

        argument: String(arguments[convCount])

      };

    }

    strings[strings.length] = string.substring(matchPosEnd);
    if (matches.length == 0) { return string; }

    if ((arguments.length - 1) < convCount) { return null; }
    var code = null;

    var match = null;

    var i = null;
    for (i=0; i<matches.length; i++) {
      if (matches[i].code == '%') { substitution = '%' }

      else if (matches[i].code == 'b') {

        matches[i].argument = String(Math.abs(parseInt(matches[i].argument)).toString(2));

        substitution = sprintfWrapper.convert(matches[i], true);

      }

      else if (matches[i].code == 'c') {

        matches[i].argument = String(String.fromCharCode(parseInt(Math.abs(parseInt(matches[i].argument)))));

        substitution = sprintfWrapper.convert(matches[i], true);

      }

      else if (matches[i].code == 'd') {

        matches[i].argument = String(Math.abs(parseInt(matches[i].argument)));

        substitution = sprintfWrapper.convert(matches[i]);

      }

      else if (matches[i].code == 'f') {

        matches[i].argument = String(Math.abs(parseFloat(matches[i].argument)).toFixed(matches[i].precision ? matches[i].precision : 6));

        substitution = sprintfWrapper.convert(matches[i]);

      }

      else if (matches[i].code == 'o') {

        matches[i].argument = String(Math.abs(parseInt(matches[i].argument)).toString(8));

        substitution = sprintfWrapper.convert(matches[i]);

      }

      else if (matches[i].code == 's') {

        matches[i].argument = matches[i].argument.substring(0, matches[i].precision ? matches[i].precision : matches[i].argument.length)

        substitution = sprintfWrapper.convert(matches[i], true);

      }

      else if (matches[i].code == 'x') {

        matches[i].argument = String(Math.abs(parseInt(matches[i].argument)).toString(16));

        substitution = sprintfWrapper.convert(matches[i]);

      }

      else if (matches[i].code == 'X') {

        matches[i].argument = String(Math.abs(parseInt(matches[i].argument)).toString(16));

        substitution = sprintfWrapper.convert(matches[i]).toUpperCase();

      }

      else {

        substitution = matches[i].match;

      }
      newString += strings[i];

      newString += substitution;
    }

    newString += strings[i];
    return newString;
  },
  convert : function(match, nosign){

    if (nosign) {

      match.sign = '';

    } else {

      match.sign = match.negative ? '-' : match.sign;

    }

    var l = match.min - match.argument.length + 1 - match.sign.length;

    var pad = new Array(l < 0 ? 0 : l).join(match.pad);

    if (!match.left) {

      if (match.pad == "0" || nosign) {

        return match.sign + pad + match.argument;

      } else {

        return pad + match.sign + match.argument;

      }

    } else {

      if (match.pad == "0" || nosign) {

        return match.sign + match.argument + pad.replace(/0/g, ' ');

      } else {

        return match.sign + match.argument + pad;

      }

    }

  }

}
sprintf = sprintfWrapper.init;

如果只是想进行简单的位置变量内容替换而不需要额外的格式化处理的话,可以用比较简单的 YUI tools 中所提供的printf:

YAHOO.Tools.printf = function() {

  var num = arguments.length;

  var oStr = arguments[0];

  for (var i = 1; i < num; i++) {

    var pattern = "\\{" + (i-1) + "\\}";

    var re = new RegExp(pattern, "g");

    oStr = oStr.replace(re, arguments[i]);

  }

  return oStr;

}

使用的时候像 YAHOO.Tools.printf("显示字符串 {0} , {1}。", "1", "2"); 这样用{?}来做匹配。

Javascript 相关文章推荐
网页里控制图片大小的相关代码
Jun 25 Javascript
在html页面中包含共享页面的方法
Oct 24 Javascript
javascript中传统事件与现代事件
Jun 23 Javascript
vueJS简单的点击显示与隐藏的效果【实现代码】
May 03 Javascript
让编辑器支持word复制黏贴、截屏的js代码
Oct 17 Javascript
微信小程序 实现拖拽事件监听实例详解
Nov 16 Javascript
JS公共小方法之判断对象是否为domElement的实例
Nov 25 Javascript
使用JavaScript开发跨平台的桌面应用详解
Jul 27 Javascript
Vue 2.0学习笔记之使用$refs访问Vue中的DOM
Dec 19 Javascript
微信小程序之事件交互操作实例分析
Dec 03 Javascript
理解JavaScript中的对象
Aug 25 Javascript
WebWorker 封装 JavaScript 沙箱详情
Nov 02 Javascript
javascript批量修改文件编码格式的方法
Jan 27 #Javascript
JavaScript中的包装对象介绍
Jan 27 #Javascript
浅谈JSON中stringify 函数、toJosn函数和parse函数
Jan 26 #Javascript
浅谈JavaScript Math和Number对象
Jan 26 #Javascript
js判断一个字符串是否包含一个子串的方法
Jan 26 #Javascript
javascript中Object使用详解
Jan 26 #Javascript
JQuery中的事件及动画用法实例
Jan 26 #Javascript
You might like
站长助手-网站web在线管理程序 v1.0 下载
2007/05/12 PHP
防止MySQL注入或HTML表单滥用的PHP程序
2009/01/21 PHP
php限制上传文件类型并保存上传文件的方法
2015/03/13 PHP
php 二维数组快速排序算法的实现代码
2017/10/17 PHP
js获取变量
2006/08/24 Javascript
用showModalDialog弹出页面后,提交表单总是弹出一个新窗口
2009/07/18 Javascript
使用jQuery简化Ajax开发 Ajax开发入门
2009/10/14 Javascript
JavaScript格式化数字的函数代码
2010/11/30 Javascript
JavaScript 高级篇之闭包、模拟类,继承(五)
2012/04/07 Javascript
jquery移动listbox的值原理及代码
2013/05/03 Javascript
基于Jquery+div+css实现弹出登录窗口(代码超简单)
2015/10/27 Javascript
Google Maps基础及实例解析
2016/08/06 Javascript
Angular的事件和表单详解
2016/12/26 Javascript
Vue 无限滚动加载指令实现方法
2019/05/28 Javascript
详解Nuxt.js中使用Element-UI填坑
2019/09/06 Javascript
解决layui laydate 时间控件一闪而过的问题
2019/09/28 Javascript
vue子组件改变父组件传递的prop值通过sync实现数据双向绑定(DEMO)
2020/02/01 Javascript
vue图片裁剪插件vue-cropper使用方法详解
2020/12/16 Vue.js
python 实时遍历日志文件
2016/04/12 Python
python机器学习理论与实战(一)K近邻法
2021/01/28 Python
python生成器,可迭代对象,迭代器区别和联系
2018/02/04 Python
浅谈Python Opencv中gamma变换的使用详解
2018/04/02 Python
Tensorflow 多线程与多进程数据加载实例
2020/02/05 Python
python 实现端口扫描工具
2020/12/18 Python
使用CSS3的font-face字体嵌入样式的方法讲解
2016/05/13 HTML / CSS
J2EE是技术还是平台还是框架
2016/08/14 面试题
优秀的毕业生的自我评价
2013/12/12 职场文书
服装设计行业个人的自我评价
2013/12/20 职场文书
高中家长寄语
2014/04/02 职场文书
汽车广告策划方案
2014/05/31 职场文书
电子商务实训报告总结
2014/11/05 职场文书
三方协议书
2015/01/27 职场文书
民事二审代理词
2015/05/25 职场文书
大学军训口号大全
2015/12/24 职场文书
python 爬取豆瓣网页的示例
2021/04/13 Python
集英社今正式宣布 成立游戏公司“集英社Games”
2022/03/31 其他游戏