javascript下利用arguments实现string.format函数
javascript下利用arguments实现string.format函数
发布时间:2016-12-30 来源:查字典编辑
摘要:下面摘抄一下源码,深入分析一下他的设计实现思路:复制代码代码如下:functionformat(string){varargs=argume...

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

复制代码 代码如下:

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教程学习
热门Javascript教程学习
编程开发子分类