浏览 4082 次
锁定老帖子 主题:Scala:使用Curry实现AOP
精华帖 (0) :: 良好帖 (4) :: 新手帖 (0) :: 隐藏帖 (0)
|
|
---|---|
作者 | 正文 |
发表时间:2011-01-28
最后修改:2011-01-28
见代码及注释,欢迎喜欢Scala的同学一起讨论: //trait里没有任何抽象的值或方法 trait AOP{ private var targets=List[Function1[String,Any]]() //List里放的都是函数对象 private val placeholder="" //无意义,用来调用函数对象的 def before=println("before...") def after=println("after...") def invoke(target:Function1[String,Any])={ //参数是个函数对象 before target(placeholder) //什么时候调用,自己放置顺序 after } def add(t:Function1[String,Any])= targets=t::targets //收集所有被拦截的方法(函数对象) def invokeAll()={ before targets.reverse.foreach(t=>t(placeholder)) //reverse:保证调用的顺序(FIFO) after //这里需要一个清空targets的方法,就不写了 } } class Write extends AOP{ def writeOne(x:String,y:String)(placeholder:String)={ //curry化,最后一个placeholder算是冗余参数 println("one working..."+x+y) } def writeTwo(x:String,y:String,z:String)(placeholder:String)={ println("two working..."+x+y+z) } } val w=new Write() w.invoke(w.writeOne("hello"," world")_) //拦截的方式,使用了偏应用函数 w.add(w.writeOne("hello"," world")_) //收集 w.add(w.writeTwo("hello"," world"," more")_) //再收集 w.invokeAll //统一拦截 这里只是给喜欢Scala的同学一个思路,期望在此思路上进行扩展。 是不是很优雅? 还在等什么,快快加入到Scala的学习队伍中来吧。 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2011-01-30
最后修改:2011-01-30
使用trait实现AOP的一般思路是利用它的stackable modification特性。我平时接触的AOP多在一个实现上进行若干次切面,楼主这个正好相反,倾向于基于多个实现的顺序调用,对应固定的两个切面(一个before一个after),这样就更象使用了偏函数的observer模式,没有更详细的场景不好更深入讨论下去。
如果按常规AOP套路考虑,我觉得重点是切面(before/after)的灵活性,比如,可以绑多个before/after方法,其签名与主实现一致,同时考虑before里可以控制是否把控制转向下一个,after里可以拿到主实现的返回值等等。这个在scala里由于有更强大的类型系统和偏函数等概念,会更有意思,我也没想清楚,请大家继续讨论。 |
|
返回顶楼 | |
发表时间:2011-02-01
Scala作为函数式语言,根本用不着什么通用AOP把,随手一个Curry函数,就实现了
|
|
返回顶楼 | |
发表时间:2011-02-01
最后修改:2011-02-01
sirxenofex 写道 Scala作为函数式语言,根本用不着什么通用AOP把,随手一个Curry函数,就实现了
刚入javaeye就又见到placeholder你的aop了,呵呵 不过这里主要展示的还是trait,curry好像没怎么用到,是否标题有误 同样的,sirxenofex为什么会认为不需要切面aop呢 希望神样的scala在中国的推广越来越好!!! |
|
返回顶楼 | |
发表时间:2011-03-19
mefan 写道 不过这里主要展示的还是trait,curry好像没怎么用到,是否标题有误 偏应用函数的实现得益于curry化 |
|
返回顶楼 | |