建议37:推荐使用replace(2)
在上面的示例代码中,函数f()的参数为特殊字符“$1”,它表示正则表达式/(bw+b)/中小括号每次匹配的文本。然后在函数体内对这个匹配文本进行处理,截取其首字母并转换为大写形式,之后返回新处理的字符串。replace方法能够在原文本中使用这个返回的新字符串替换每次匹配的子字符串。
对于上面的示例,可以使用小括号来获取更多匹配文本的信息。例如,直接利用小括号传递单词的首字母,然后进行大小写转换处理:
- var s = 'script language = "javaScript" type= " text / javaScript"';
- var f = function($1,$2,$3){
- return $2.toUpperCase()+$3;
- }
- var a = s.replace( /b(w)(w*)b/g, f );
//Script Language = "JavaScript" Type = " Text /JavaScript"
在函数f()中,第一个参数表示每次匹配的文本,第二个参数表示第一个小括号的子表达式所匹配的文本,即单词的首字母,第二个参数表示第二个小括号的子表达式所匹配的文本。
实际上,replace方法的第二个参数(函数式参数)不需要传递任何形参,replace方法依然会向它传递多个实参,这些实参都包含一定的意思,具体说明如下:
第一个参数表示与匹配模式相匹配的文本,如上面示例中每次匹配的单词字符串。
其后的参数是与匹配模式中子表达式相匹配的字符串,参数个数不限,根据子表达式数而定。
后面的参数是一个整数,表示匹配文本在字符串中的下标位置。
最后一个参数表示字符串自身。
例如,将上面示例中替换文本函数改为如下形式。
- var f = function(){
- return arguments[1].toUpperCase()+arguments[2];
- }
如果不为函数传递形参,直接调用函数的arguments属性,同样能够读取到正则表达式中相关匹配文本的信息。
arguments[0]表示每次匹配的单词。
arguments[1]表示第一个子表达式匹配的文本,即单词的首字母。
arguments[2]表示第二个子表达式匹配的文本,即单词的余下字母。
arguments[3]表示匹配文本的下标位置,如第一个匹配单词“script”的下标位置就是0,依此类推。
arguments[4]表示要执行匹配的字符串,这里表示“script language = "javascript" type= " text / javascript"”。
- var s = 'script language = "javascript" type= " text / javascript"';
- var f = function(){
- for( var i = 0; i < arguments.length; i ++ ){
- alert("第"+(i+1)+"个参数的值:"+arguments[i]);
- }
- }
- var a = s.replace( /b(w)(w*)b/g, f );
在函数体中,使用for循环结构遍历argumnets属性,每次匹配单词时,都会弹出5次提示信息,分别显示上面所列的匹配文本信息。其中,arguments[1]、arguments[2]会根据每次匹配文本不同,分别显示当前匹配文本中子表达式匹配的信息,arguments[3]显示当前匹配单词的下标位置。而arguments[0]总是显示每次匹配的单词,arguments[4]总是显示被操作的字符串。
例如,下面代码能够自动提取字符串中的分数,进行汇总后算出平均分,然后利用replace方法提取每个分值,与平均分进行比较以决定替换文本的具体信息。
- var s = "张三56分,李四74分,王五92分,赵六84分";
- var a = s.match( /d+/g ), sum = 0;
- for( var i= 0 ; i
- sum += parseFloat(a[i]);
};var avg = sum / a.length;function f(){var n = parseFloat(arguments[1]);return n + "分" + " ( " + (( n > avg ) ? ( "超出平均分" + ( n - avg ) ) :( "低于平均分" + ( avg - n ) )) + "分 ) ";}var ss1 = s.replace( /(d+)分/g, f );
alert( s1 );/ "张三56分(低于平均分20.5分),李四74分(低于平均分2.5分),王五92分(超出平均分15.5分), 赵六84分 ( 超出平均分7.5分)"/
在上面的示例中,遍历数组时不能够使用for in语句,因为这个数组中还存储着其他相关的匹配文本信息。应该使用for结构来实现。由于截取的数字都是字符串类型,所以应该把它们都转换为数值类型,否则会被误解,如把数字连接在一起,或者按字母顺序进行比较等。