javascript设计模式交流(2)
2010-09-14 13:17:16 来源:WEB开发网 闂傚倸鍊搁崐鎼佸磹閹间礁纾归柟闂寸绾惧綊鏌熼梻瀵割槮缁炬儳缍婇弻鐔兼⒒鐎靛壊妲紒鐐劤缂嶅﹪寮婚悢鍏尖拻閻庨潧澹婂Σ顔剧磼閹冣挃闁硅櫕鎹囬垾鏃堝礃椤忎礁浜鹃柨婵嗙凹缁ㄧ粯銇勯幒瀣仾闁靛洤瀚伴獮鍥敍濮f寧鎹囬弻鐔哥瑹閸喖顬堝銈庡亝缁挸鐣烽崡鐐嶆棃鍩€椤掑嫮宓佸┑鐘插绾句粙鏌涚仦鎹愬闁逞屽墰閹虫捇锝炲┑瀣╅柍杞拌兌閻ゅ懐绱撴担鍓插剱妞ゆ垶鐟╁畷銉р偓锝庡枟閻撴洘銇勯幇闈涗簼缂佽埖姘ㄧ槐鎾诲礃閳哄倻顦板┑顔硷工椤嘲鐣烽幒鎴旀瀻闁规惌鍘借ⅵ濠电姷鏁告慨顓㈠磻閹剧粯鈷戞い鎺嗗亾缂佸鏁婚獮鍡涙倷閸濆嫮顔愬┑鐑囩秵閸撴瑦淇婇懖鈺冪<闁归偊鍙庡▓婊堟煛鐏炵硶鍋撻幇浣告倯闁硅偐琛ラ埀顒冨皺閺佹牕鈹戦悙鏉戠仸闁圭ǹ鎽滅划鏃堟偨缁嬭锕傛煕閺囥劌鐏犻柛鎰ㄥ亾婵$偑鍊栭崝锕€顭块埀顒佺箾瀹€濠侀偗婵﹨娅g槐鎺懳熺拠鑼舵暱闂備胶枪濞寸兘寮拠宸殨濠电姵纰嶉弲鎻掝熆鐠虹尨宸ョ€规挸妫濆铏圭磼濡搫顫嶇紓浣风劍閹稿啿鐣烽幋锕€绠婚悹鍥у级瀹撳秴顪冮妶鍡樺鞍缂佸鍨剁粋宥夋倷椤掍礁寮垮┑鈽嗗灣閸樠勭妤e啯鍊垫慨妯煎亾鐎氾拷

这是一个标准的状态机处理词法分析的例子,事实上,有些简单的解释器模式,仅仅通过词法分析即可实现,功能可以写在状态改变函数中,而无需对产生的token流进行处理。
函数式语言特性与状态机模式
作为函数式语言,js实现解释器模式有非常有趣的方式:以不定个数的参数形式传入函数进行处理,这样可以方便的扩展功能,同时可以使用户更自由的使用解释器提供的接口。
下面一段代码是一个用于日期对象的格式化的类 它是状态机词法分析的一个稍微复杂的例子,同时它以函数参数的方式为用户提供了扩展功能。
/*
DateEx类
说明:以参数形式继承自Date对象为Date对象扩展方法
方法:
format(formatString,[fun],......)
参数:
formatString:格式字符串将日期转换成所规定的格式字符串
格式说明:
%[x]:
[x]代表日期的一个部分
%y:年
%m:月
%d:日
%w:星期
%h:小时
%i:分
%s:秒
%[num][x]:
[num]代表长度[x]意义同上如果长度不足则用0补齐如果长度超出[num]则将高位截断
%f[x]:
以自定义函数处理%[x]得到的值,自定义函数在参数列表[fun]中给出,参数中[fun]的个数应与%f[x]的数目一致
fun:可选的,处理函数,当格式字符串中有格式符%f出现时,则在fun中取相应的函数处理
*/
functionDateEx(date){
date=date||newDate();
date.format=function(formatString)
{
varf;
varj=0;
functionfbuilder(n){
returnfunction(v){
vars=v.toString();
if(s.length>=n)returns.slice(s.length-n,s.length);
if(s.length<n)returnnewArray(n-s.length+1).join(0)+s;
};
}
varargs=arguments;
varresault=newString();
var_1=function(c)//状态1是读入格式字符串的状态
{
if(c!="%")//对于非%字符按原样输出
{
resault+=c;
return_1;
}
else//读到%时进入状态2否则延续状态1
{
return_2;
}
};
var_2=function(c)//状态2是读入特殊格式字符串的状态
{
if(c.match(/d/)!=null)//对于数字构造相应处理函数返回状态3
{
f=fbuilder(Number(c));
return_3;
}
elseif(c=="f")//对于格式符f从参数中获取相应处理函数返回状态3
{
f=args[++j];
return_3;
}
else//没有特殊格式符直接进入状态3
{
f=function(v){returnv;}
return_3(c);
}
};
var_3=function(c)
{
if(c=="%")//格式符%连续2个%将被转义为一个%返回状态1
{
resault+=c;
return_1;
}
elseif(c=="y")//格式符y取出年份返回状态1
{
resault+=f(date.getFullYear());
return_1;
}
elseif(c=="m")//格式符m取出月份返回状态1
{
resault+=f(date.getMonth()+1);
return_1;
}
elseif(c=="d")//格式符d取出日期返回状态1
{
resault+=f(date.getDate());
return_1;
}
elseif(c=="w")//格式符w取出星期返回状态1
{
resault+=f(date.getDay());
return_1;
}
elseif(c=="h")//格式符h取出小时返回状态1
{
resault+=f(date.getHours());
return_1;
}
elseif(c=="i")//格式符i取出分返回状态1
{
resault+=f(date.getMinutes());
return_1;
}
elseif(c=="s")//格式符s取出秒返回状态1
{
resault+=f(date.getSeconds());
return_1;
}
elsereturn_1//没有合法格式符忽略返回状态1
};
varstatus=_1;
for(vari=0;i<formatString.length;i++)
{
status=status(formatString.charAt(i));
}
returnresault;
}
returndate;
}
varweekdays="日一二三四五六"
document.write(newDateEx().format("%2y-%2m-%2d星期%fw%2h:%2i:%2s%%",function(v){returnweekdays.charAt(v);}))
Tags:javascript 设计模式 交流
编辑录入:爽爽 [复制链接] [打 印]更多精彩
赞助商链接