javascript下利用arguments实现string.format函数


Posted in Javascript onAugust 24, 2010

下面摘抄一下源码,深入分析一下他的设计实现思路:

function format(string) { 
var args = arguments; 
var pattern = new RegExp("%([1-" + arguments.length + "])", "g"); 
return String(string).replace(pattern, function(match, index) { 
return args[index]; 
}); 
};

通过format函数,下面的代码:
format("And the %1 want to know whose %2 you %3", "papers", "shirt", "wear");

就会返回:"And the papers want to know whose shirt you wear" 。
果然有点像c#下string.format函数一样传参调用。
总体说来,好像真没什么技术含量。但是真的没有技术含量吗?楼猪大胆根据自己对javascript和arguments的浅薄认识和理解,再来剖析一下这段程序:
1、正则表达式
非常巧妙地new了一个以%开头匹配1到argument个数的一个正则pattern,这个正则是下面第2点字符串替换的重要前提准备;
2、string的Replace函数
replace函数的第二个参数是function,这点非常令人“意外”。通过定义,变量args实际上就是arguments,接着通过args[index]就能取到第index个参数,而且index>=1且index<arguments.length又能保证获取参数的正确。

函数如此短小精悍,和强大的功能形成巨大反差,令人拍案。
可能有许多像楼猪一样被c#惯坏的开发者,会迷恋c#的string.format的写法(大部分还是使用习惯在作怪吧?),好事楼猪稍微改动了一下源码:

function format(string) { 
var args = arguments; 
var pattern = new RegExp("{([0-" + arguments.length + "])}", "g"); 
return String(string).replace(pattern, function(match, index) { 
var currentIndex = parseInt(index); 
if (currentIndex + 1 > args.length || currentIndex < 0) { 
throw new Error("参数索引出错"); 
} 
return args[currentIndex + 1]; 
}); 
}; 
document.write(format("And the {0} want to know whose {1} you {2}", "papers", "shirt", "wear"));//大括号,索引从0开始...

这样看上去就可以像c#的编写风格一样调用format函数了。
最后查看此文的写作时间是在2008年,楼猪在08年的时候觉悟还算蛮高的,正自发努力学习javascript中,但是对arguments认识还很稚嫩,虽然已经知道可以在自定义事件中通过它来定义createFunction函数,用createFunction函数来构造无参数的function给事件使用,但是当时一直抑郁“只知其形,不得其实”。看完Andrew的佳作,豁然开朗,虽然反应迟钝后知后觉,依然感到无比振奋和欣慰。

你看一下Andrew Tetlaw的原文吧。其实下面已经有人指出format函数参数超出9以后,该函数就不起作用了,然后还给出了解决方法:

eric d. Hi, thanks for that brilliant article. Made a lot of things a lot clearer!
Note: new RegExp("%([1-" + arguments.length + "])", "g"); will fail passed 9 arguments (the regexp would be "%([1-10])" so it will only match %0 and %1).

I think an easy fix would be something like:
function format(string) { var args = arguments; var pattern = new RegExp("%([0-9]+)", "g"); return String(string).replace(pattern, function(match, index) { if (index == 0 || index >= args.length) throw "Invalid index in format string"; return args[index]; }); };
(Sorry for nitpicking, I understand it was only an example and brevety is the main objective, but its a great function to have)

Posted on: January 20th 2009, 12:01 am

Javascript 相关文章推荐
计算世界完全对称日的js代码,粗糙版
Nov 04 Javascript
JS打开新窗口的2种方式
Apr 18 Javascript
Query中click(),bind(),live(),delegate()的区别
Nov 19 Javascript
jQuery获取和设置表单元素的方法
Feb 14 Javascript
jquery validate 自定义验证方法介绍 日期验证
Feb 27 Javascript
JQuery节点元素属性操作方法
Jun 11 Javascript
js实现的万能flv网页播放器代码
Apr 30 Javascript
基于jQuery倒计时插件实现团购秒杀效果
May 13 Javascript
js中常用的Tab切换效果(推荐)
Aug 30 Javascript
移动端触摸滑动插件swiper使用方法详解
Aug 11 Javascript
基于Vue 服务端Cookies删除的问题
Sep 21 Javascript
解决Vue-cli3没有vue.config.js文件夹及配置vue项目域名的问题
Dec 04 Vue.js
基于jQuery的淡入淡出可自动切换的幻灯插件
Aug 24 #Javascript
js null,undefined,字符串小结
Aug 21 #Javascript
javascript中的float运算精度实例分析
Aug 21 #Javascript
Firebug入门指南(Firefox浏览器)
Aug 21 #Javascript
jquery插件之easing 动态菜单
Aug 21 #Javascript
url地址自动加#号问题说明
Aug 21 #Javascript
jquery中输入验证中一个不错的效果
Aug 21 #Javascript
You might like
地摊中国 - 珍藏老照片
2020/08/18 杂记
PHP也可以?成Shell Script
2006/10/09 PHP
PHP COOKIE及时生效的方法介绍
2014/02/14 PHP
PHP计算一年多少个星期和每周的开始和结束日期
2014/07/01 PHP
php树型类实例
2014/12/05 PHP
dedecms集成财付通支付接口
2014/12/28 PHP
CodeIgniter框架数据库基本操作示例
2018/05/24 PHP
如何让您的中波更粗更长 - 中波框形天线制作
2021/03/10 无线电
利用jQuery插件扩展识别浏览器内核与外壳的类型和版本的实现代码
2011/10/22 Javascript
仿中关村在线首页弹出式广告插件(jQuery版)
2012/05/03 Javascript
简述AngularJS的控制器的使用
2015/06/16 Javascript
用JavaScript获取页面文档内容的实现代码
2016/06/10 Javascript
JavaScript中的Reflect对象详解(ES6新特性)
2016/07/22 Javascript
在web中js实现类似excel的表格控件
2016/09/01 Javascript
基于JS实现移动端向左滑动出现删除按钮功能
2017/02/22 Javascript
JavaScript限制在客户区可见范围的拖拽(解决scrollLeft和scrollTop的问题)(2)
2017/05/17 Javascript
基于复选框demo(分享)
2017/09/27 Javascript
angular json对象push到数组中的方法
2018/02/27 Javascript
JavaScript使用递归和循环实现阶乘的实例代码
2018/08/28 Javascript
原生js检测页面加载完毕的实例
2018/09/11 Javascript
[原创]微信小程序获取网络类型的方法示例
2019/03/01 Javascript
JavaScript实现无限轮播效果
2020/11/19 Javascript
python实现汉诺塔递归算法经典案例
2021/03/01 Python
浅谈python中get pass用法
2019/03/19 Python
python网络爬虫 CrawlSpider使用详解
2019/09/27 Python
Python脚本操作Excel实现批量替换功能
2019/11/20 Python
I.T中国官网:精选时尚设计师单品网购平台
2018/03/26 全球购物
澳大利亚在线家具店:Luxo Living
2019/03/24 全球购物
Visual-Click葡萄牙:欧洲领先的在线眼镜商
2020/02/17 全球购物
西安交大自主招生自荐信
2014/01/27 职场文书
药剂专业自荐信范文
2014/04/16 职场文书
加油口号大全
2014/06/13 职场文书
治庸问责心得体会
2014/09/12 职场文书
会计求职自荐信
2015/03/26 职场文书
2016年共产党员公开承诺书
2016/03/24 职场文书
分享Python异步爬取知乎热榜
2022/04/12 Python