青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

隨筆-341  評(píng)論-2670  文章-0  trackbacks-0
    雖然說(shuō)分析語(yǔ)法樹(shù)依賴于遞歸,但是你真的去寫(xiě)遞歸那是一件很煩的事情,個(gè)人覺(jué)得煩事煩在你每次都要去RegexExpression.h里面聲明所有的虛函數(shù)之后復(fù)制過(guò)來(lái)一一運(yùn)行。有沒(méi)有辦法僅編輯.cpp文件就能做到呢?也就是說(shuō),在如何不修改Expression一系列類的接口的情況下給Expression添加算法?一般來(lái)說(shuō)對(duì)付樹(shù)形結(jié)構(gòu)都是使用Visitor模式的。

    首先對(duì)于上一篇文章定義的樹(shù)來(lái)看,我們需要設(shè)計(jì)一個(gè)通用的Visitor接口:
 1         class IRegexExpressionAlgorithm : public Interface
 2         {
 3         public:
 4             virtual void                Visit(CharSetExpression* expression)=0;
 5             virtual void                Visit(LoopExpression* expression)=0;
 6             virtual void                Visit(SequenceExpression* expression)=0;
 7             virtual void                Visit(AlternateExpression* expression)=0;
 8             virtual void                Visit(BeginExpression* expression)=0;
 9             virtual void                Visit(EndExpression* expression)=0;
10             virtual void                Visit(CaptureExpression* expression)=0;
11             virtual void                Visit(MatchExpression* expression)=0;
12             virtual void                Visit(PositiveExpression* expression)=0;
13             virtual void                Visit(NegativeExpression* expression)=0;
14             virtual void                Visit(UsingExpression* expression)=0;
15         };

    接口定義好了之后,就給所有的表達(dá)式樹(shù)添加一個(gè)Apply(虛)函數(shù)來(lái)訪問(wèn)相應(yīng)的Visit函數(shù):
 1         void CharSetExpression::Apply(IRegexExpressionAlgorithm& algorithm)
 2         {
 3             algorithm.Visit(this);
 4         }
 5 
 6         void LoopExpression::Apply(IRegexExpressionAlgorithm& algorithm)
 7         {
 8             algorithm.Visit(this);
 9         }
10 
11         void SequenceExpression::Apply(IRegexExpressionAlgorithm& algorithm)
12         {
13             algorithm.Visit(this);
14         }
15 
16         void AlternateExpression::Apply(IRegexExpressionAlgorithm& algorithm)
17         {
18             algorithm.Visit(this);
19         }
20 
21         void BeginExpression::Apply(IRegexExpressionAlgorithm& algorithm)
22         {
23             algorithm.Visit(this);
24         }
25 
26         void EndExpression::Apply(IRegexExpressionAlgorithm& algorithm)
27         {
28             algorithm.Visit(this);
29         }
30 
31         void CaptureExpression::Apply(IRegexExpressionAlgorithm& algorithm)
32         {
33             algorithm.Visit(this);
34         }
35 
36         void MatchExpression::Apply(IRegexExpressionAlgorithm& algorithm)
37         {
38             algorithm.Visit(this);
39         }
40 
41         void PositiveExpression::Apply(IRegexExpressionAlgorithm& algorithm)
42         {
43             algorithm.Visit(this);
44         }
45 
46         void NegativeExpression::Apply(IRegexExpressionAlgorithm& algorithm)
47         {
48             algorithm.Visit(this);
49         }
50 
51         void UsingExpression::Apply(IRegexExpressionAlgorithm& algorithm)
52         {
53             algorithm.Visit(this);
54         }

    于是我們可以去實(shí)現(xiàn)一個(gè)IRegexExpressionAlgorithm了。但是事情還沒(méi)完。如果每一個(gè)算法都要去實(shí)現(xiàn)一個(gè)IRegexExpressionAlgorithm的話,我們會(huì)發(fā)現(xiàn)因?yàn)樗惴ㄋ枰膮?shù)不同,為了使用Visit這種無(wú)參數(shù)的函數(shù),我們都需要為每一個(gè)具體的Apply實(shí)現(xiàn)一次參數(shù)的緩存工作。但是因?yàn)閰?shù)是未知的,而且模板函數(shù)又不能是虛函數(shù)(所以不能把Expression::Apply寫(xiě)成模板函數(shù)),所以IRegexExpressionAlgorithm的Visit系列函數(shù)是沒(méi)有參數(shù)的。因此一個(gè)輔助類就應(yīng)運(yùn)而生了。

    這個(gè)輔助類用來(lái)給你很直接地寫(xiě)具有一個(gè)參數(shù)的算法。你只要?jiǎng)?chuàng)建它,然后寫(xiě)完所有的(算法類里面的)Apply函數(shù)就行了。那么你怎么在一個(gè)表達(dá)式上面調(diào)用你自己的算法呢?假設(shè)參數(shù)是p,我們希望只需要簡(jiǎn)單地執(zhí)行Invoke(expression, p)就可以調(diào)用到自己了。所以這里實(shí)現(xiàn)了一個(gè)RegexExpressionAlgorithm<ReturnType, ParameterType>。當(dāng)然對(duì)于ReturnType==void的時(shí)候,我們還需要再特化一個(gè),不過(guò)這個(gè)就不說(shuō)了:
 1         template<typename ReturnType, typename ParameterType=void*>
 2         class RegexExpressionAlgorithm : public Object, public IRegexExpressionAlgorithm
 3         {
 4         private:
 5             ReturnType                    returnValue;
 6             void*                        parameterValue;
 7         public:
 8 
 9             ReturnType Invoke(Expression* expression, ParameterType parameter)
10             {
11                 parameterValue=(void*)&parameter;
12                 expression->Apply(*this);
13                 return returnValue;
14             }
15 
16             ReturnType Invoke(Expression::Ref expression, ParameterType parameter)
17             {
18                 parameterValue=(void*)&parameter;
19                 expression->Apply(*this);
20                 return returnValue;
21             }
22 
23             virtual ReturnType            Apply(CharSetExpression* expression, ParameterType parameter)=0;
24             virtual ReturnType            Apply(LoopExpression* expression, ParameterType parameter)=0;
25             virtual ReturnType            Apply(SequenceExpression* expression, ParameterType parameter)=0;
26             virtual ReturnType            Apply(AlternateExpression* expression, ParameterType parameter)=0;
27             virtual ReturnType            Apply(BeginExpression* expression, ParameterType parameter)=0;
28             virtual ReturnType            Apply(EndExpression* expression, ParameterType parameter)=0;
29             virtual ReturnType            Apply(CaptureExpression* expression, ParameterType parameter)=0;
30             virtual ReturnType            Apply(MatchExpression* expression, ParameterType parameter)=0;
31             virtual ReturnType            Apply(PositiveExpression* expression, ParameterType parameter)=0;
32             virtual ReturnType            Apply(NegativeExpression* expression, ParameterType parameter)=0;
33             virtual ReturnType            Apply(UsingExpression* expression, ParameterType parameter)=0;
34         public:
35             void Visit(CharSetExpression* expression)
36             {
37                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
38             }
39 
40             void Visit(LoopExpression* expression)
41             {
42                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
43             }
44 
45             void Visit(SequenceExpression* expression)
46             {
47                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
48             }
49 
50             void Visit(AlternateExpression* expression)
51             {
52                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
53             }
54 
55             void Visit(BeginExpression* expression)
56             {
57                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
58             }
59 
60             void Visit(EndExpression* expression)
61             {
62                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
63             }
64 
65             void Visit(CaptureExpression* expression)
66             {
67                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
68             }
69 
70             void Visit(MatchExpression* expression)
71             {
72                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
73             }
74 
75             void Visit(PositiveExpression* expression)
76             {
77                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
78             }
79 
80             void Visit(NegativeExpression* expression)
81             {
82                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
83             }
84 
85             void Visit(UsingExpression* expression)
86             {
87                 returnValue=Apply(expression, *((ParameterType*)parameterValue));
88             }
89         };

    好了,讓我們使用它來(lái)實(shí)現(xiàn)之前提到過(guò)的IsEqual功能吧。首先實(shí)現(xiàn)一個(gè)IsEqualAlgorithm:
  1         class IsEqualAlgorithm : public RegexExpressionAlgorithm<bool, Expression*>
  2         {
  3         public:
  4             bool Apply(CharSetExpression* expression, Expression* target)
  5             {
  6                 CharSetExpression* expected=dynamic_cast<CharSetExpression*>(target);
  7                 if(expected)
  8                 {
  9                     if(expression->reverse!=expected->reverse)return false;
 10                     if(expression->ranges.Count()!=expected->ranges.Count())return false;
 11                     for(int i=0;i<expression->ranges.Count();i++)
 12                     {
 13                         if(expression->ranges[i]!=expected->ranges[i])return false;
 14                     }
 15                     return true;
 16                 }
 17                 return false;
 18             }
 19 
 20             bool Apply(LoopExpression* expression, Expression* target)
 21             {
 22                 LoopExpression* expected=dynamic_cast<LoopExpression*>(target);
 23                 if(expected)
 24                 {
 25                     if(expression->min!=expected->min)return false;
 26                     if(expression->max!=expected->max)return false;
 27                     if(!Invoke(expression->expression, expected->expression.Obj()))return false;
 28                     return true;
 29                 }
 30                 return false;
 31             }
 32 
 33             bool Apply(SequenceExpression* expression, Expression* target)
 34             {
 35                 SequenceExpression* expected=dynamic_cast<SequenceExpression*>(target);
 36                 if(expected)
 37                 {
 38                     if(!Invoke(expression->left, expected->left.Obj()))return false;
 39                     if(!Invoke(expression->right, expected->right.Obj()))return false;
 40                     return true;
 41                 }
 42                 return false;
 43             }
 44 
 45             bool Apply(AlternateExpression* expression, Expression* target)
 46             {
 47                 AlternateExpression* expected=dynamic_cast<AlternateExpression*>(target);
 48                 if(expected)
 49                 {
 50                     if(!Invoke(expression->left, expected->left.Obj()))return false;
 51                     if(!Invoke(expression->right, expected->right.Obj()))return false;
 52                     return true;
 53                 }
 54                 return false;
 55             }
 56 
 57             bool Apply(BeginExpression* expression, Expression* target)
 58             {
 59                 BeginExpression* expected=dynamic_cast<BeginExpression*>(target);
 60                 if(expected)
 61                 {
 62                     return true;
 63                 }
 64                 return false;
 65             }
 66 
 67             bool Apply(EndExpression* expression, Expression* target)
 68             {
 69                 EndExpression* expected=dynamic_cast<EndExpression*>(target);
 70                 if(expected)
 71                 {
 72                     return true;
 73                 }
 74                 return false;
 75             }
 76 
 77             bool Apply(CaptureExpression* expression, Expression* target)
 78             {
 79                 CaptureExpression* expected=dynamic_cast<CaptureExpression*>(target);
 80                 if(expected)
 81                 {
 82                     if(expression->name!=expected->name)return false;
 83                     if(!Invoke(expression->expression, expected->expression.Obj()))return false;
 84                     return true;
 85                 }
 86                 return false;
 87             }
 88 
 89             bool Apply(MatchExpression* expression, Expression* target)
 90             {
 91                 MatchExpression* expected=dynamic_cast<MatchExpression*>(target);
 92                 if(expected)
 93                 {
 94                     if(expression->name!=expected->name)return false;
 95                     if(expression->index!=expected->index)return false;
 96                     return true;
 97                 }
 98                 return false;
 99             }
100 
101             bool Apply(PositiveExpression* expression, Expression* target)
102             {
103                 PositiveExpression* expected=dynamic_cast<PositiveExpression*>(target);
104                 if(expected)
105                 {
106                     if(!Invoke(expression->expression, expected->expression.Obj()))return false;
107                     return true;
108                 }
109                 return false;
110             }
111 
112             bool Apply(NegativeExpression* expression, Expression* target)
113             {
114                 NegativeExpression* expected=dynamic_cast<NegativeExpression*>(target);
115                 if(expected)
116                 {
117                     if(!Invoke(expression->expression, expected->expression.Obj()))return false;
118                     return true;
119                 }
120                 return false;
121             }
122 
123             bool Apply(UsingExpression* expression, Expression* target)
124             {
125                 UsingExpression* expected=dynamic_cast<UsingExpression*>(target);
126                 if(expected)
127                 {
128                     if(expression->name!=expected->name)return false;
129                     return true;
130                 }
131                 return false;
132             }
133         };

    譬如看AlternateExpression的IsEqual方法。AlternateExpression跟Expression是否相等只需要通過(guò)比較兩個(gè)子表達(dá)式是否相等即可,于是代碼就變成了:
 1             bool Apply(AlternateExpression* expression, Expression* target)
 2             {
 3                 AlternateExpression* expected=dynamic_cast<AlternateExpression*>(target);
 4                 if(expected)
 5                 {
 6                     if(!Invoke(expression->left, expected->left.Obj()))return false;
 7                     if(!Invoke(expression->right, expected->right.Obj()))return false;
 8                     return true;
 9                 }
10                 return false;
11             }

    如果將AlternateExpression* expression變?yōu)锳lternateExpression* const this,將Invoke(a, b)換成a->IsEqual(b),就跟直接寫(xiě)IsEqual虛函數(shù)沒(méi)兩樣了。于是自己調(diào)用自己還是很方便的。但是我們最終還是想做成a->IsEqual(b)的,于是還要在Expression基類中寫(xiě)一點(diǎn):
1         bool Expression::IsEqual(vl::regex_internal::Expression *expression)
2         {
3             IsEqualAlgorithm algorithm;
4             return algorithm.Invoke(this, expression);
5         }

    于是IsEqual的實(shí)現(xiàn)就結(jié)束了。雖然Visitor直接使用會(huì)很麻煩,但是我們可以通過(guò)稍微的改造一下讓其更好用。當(dāng)然這里跟Visitor其實(shí)還不是完全一致,細(xì)節(jié)問(wèn)題就不詳細(xì)討論了。至少文章的目標(biāo)“不通過(guò)修改Expression的接口而添加新功能”的目標(biāo)已經(jīng)實(shí)現(xiàn)了。就結(jié)果來(lái)講,添加一個(gè)新的功能還是很方便的。
posted on 2009-10-17 17:34 陳梓瀚(vczh) 閱讀(2028) 評(píng)論(0)  編輯 收藏 引用 所屬分類: VL++3.0開(kāi)發(fā)紀(jì)事
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            亚洲乱码一区二区| 美腿丝袜亚洲色图| 狼人天天伊人久久| 亚洲国产乱码最新视频| 夜久久久久久| 久久影视三级福利片| 欧美三级视频在线| 黑人巨大精品欧美一区二区小视频| 亚洲国产毛片完整版| 午夜精品在线视频| 亚洲福利视频一区| 午夜亚洲影视| 欧美日韩国产小视频在线观看| 国产日韩欧美中文在线播放| 99视频有精品| 免费成人你懂的| 亚洲欧美一区二区原创| 欧美激情第3页| 国内精品美女av在线播放| 亚洲图片欧美午夜| 亚洲福利国产| 久久九九有精品国产23| 国产精品日韩在线播放| 亚洲精品乱码久久久久久日本蜜臀| 欧美亚洲日本一区| 亚洲精品在线三区| 久久亚洲精品视频| 国产性做久久久久久| 一区二区免费在线播放| 蜜臀久久久99精品久久久久久| 国产精品99久久久久久人| 免费高清在线视频一区·| 国产一区二区福利| 亚洲欧美在线免费观看| 日韩一级精品视频在线观看| 巨胸喷奶水www久久久免费动漫| 国产欧美日韩综合一区在线观看| 一区二区三区免费观看| 欧美国产日韩一二三区| 久久精品伊人| 国产手机视频精品| 欧美一区二区三区免费看| 日韩午夜在线播放| 欧美激情在线有限公司| 亚洲高清免费视频| 免费观看国产成人| 久久久99国产精品免费| 国产字幕视频一区二区| 欧美中文在线视频| 亚洲天堂网在线观看| 欧美先锋影音| 中文国产一区| 99精品热视频| 欧美四级在线观看| 亚洲一区三区在线观看| 日韩午夜电影在线观看| 欧美日韩另类视频| 亚洲视频导航| 99在线热播精品免费99热| 欧美日韩国产首页在线观看| 亚洲美女视频在线观看| 亚洲精华国产欧美| 免费在线成人| 亚洲精选视频免费看| 91久久久亚洲精品| 欧美日韩国语| 亚洲午夜精品久久久久久app| 亚洲美女免费视频| 国产精品福利片| 午夜久久影院| 午夜视频一区二区| 国内精品一区二区| 欧美成人久久| 欧美激情精品久久久久| 中文国产成人精品| 亚洲午夜av在线| 国产一二三精品| 免费久久99精品国产自| 欧美aⅴ99久久黑人专区| 99精品国产在热久久下载| 亚洲精品视频在线观看免费| 欧美伦理一区二区| 亚洲欧美在线视频观看| 欧美一区二区免费视频| 亚洲第一区中文99精品| 欧美激情二区三区| 欧美日韩国产精品专区| 小黄鸭精品aⅴ导航网站入口| 欧美一区二区三区在线视频| 在线日韩av片| 亚洲理论在线| 国产日韩综合| 欧美sm视频| 欧美视频福利| 久久免费视频网| 欧美激情视频在线免费观看 欧美视频免费一 | 在线观看视频一区二区| 亚洲国产99| 国产精品久久久久久久久久免费| 久久久999国产| 欧美大片国产精品| 欧美亚洲日本国产| 久久综合中文字幕| 亚洲免费人成在线视频观看| 欧美一区在线看| 999亚洲国产精| 欧美亚洲视频一区二区| 亚洲精品日本| 欧美一级二级三级蜜桃| 亚洲美女网站| 亚洲欧美日韩中文视频| 亚洲激情二区| 亚洲永久精品国产| 在线视频国产日韩| 亚洲一区二区精品在线| 在线日韩中文字幕| 亚洲无吗在线| 亚洲精品国产精品国自产观看| 亚洲综合精品| 日韩一本二本av| 欧美在线中文字幕| 亚洲午夜视频| 美女久久一区| 久久高清国产| 欧美日韩在线免费观看| 女人香蕉久久**毛片精品| 国产精品欧美激情| 亚洲国产清纯| 国产在线成人| 一区二区三区免费观看| 亚洲国产一区在线| 午夜精品理论片| 一本大道久久精品懂色aⅴ| 久久久久久久久久久久久9999| 亚洲一区不卡| 欧美国产日韩a欧美在线观看| 久久久久www| 国产精品盗摄一区二区三区| 亚洲国产三级| 在线观看日韩www视频免费 | 欧美一区二区三区精品| 亚洲午夜在线观看视频在线| 欧美1区2区| 久久青青草综合| 国产欧美一区二区三区在线看蜜臀| 亚洲精品国产精品国产自| 在线观看欧美日本| 久久国产精品亚洲va麻豆| 欧美一级一区| 国产精品豆花视频| 亚洲裸体在线观看| 日韩网站在线| 欧美成ee人免费视频| 免费日韩av片| 精品成人国产| 久久精品青青大伊人av| 久久精品日韩欧美| 国产欧美一区二区三区另类精品| 亚洲图片欧美日产| 亚洲欧美国产精品va在线观看 | 欧美在线短视频| 国产精品第2页| 一区二区三区福利| 亚洲宅男天堂在线观看无病毒| 欧美日韩一区在线观看视频| 91久久精品网| 亚洲看片免费| 欧美成人精品在线视频| 欧美激情精品久久久久久免费印度 | 亚洲精品中文字幕有码专区| 91久久久国产精品| 欧美成人午夜激情| 91久久亚洲| 一本色道久久综合亚洲精品高清| 欧美激情一二区| 亚洲精品偷拍| 这里只有精品在线播放| 欧美日韩精品是欧美日韩精品| 亚洲精品免费在线| 亚洲夜晚福利在线观看| 国产精品大全| 亚洲欧美日韩国产综合精品二区| 久久福利视频导航| 韩国一区二区三区在线观看 | 99亚洲一区二区| 欧美日韩一区二区在线观看视频| 日韩一级网站| 欧美一级网站| 激情欧美一区二区| 欧美成人精品一区| 日韩一级大片| 欧美在线观看日本一区| 国产一区二区三区的电影| 久久久久免费| 91久久久久久久久久久久久| 一区二区精品在线观看| 欧美午夜电影一区| 欧美在线视频a| 欧美多人爱爱视频网站| 99热这里只有成人精品国产|