高阶函数的复用与组合
2015-08-23 20:20
281 查看
原文
http://danielwestheide.com/blog/2013/01/23/the-neophytes-guide-to-scala-part-10-staying-dry-with-higher-order-functions.html
这个是边看边记录的
http://danielwestheide.com/blog/2013/01/23/the-neophytes-guide-to-scala-part-10-staying-dry-with-higher-order-functions.html
这个是边看边记录的
case class Email(subject: String,text: String,sender: String,recipient: String) object Demo { //从圆点开始抽象,我们要写的是Email => Boolean的扩展,即我们提供一个Email给表达式之外, //让后返回boolean,我们根据该boolean继续我们的工作,而函数之外就可以根据这个email组各种 //逻辑判断 type EmailFilter = Email => Boolean def newEmailsForUser (mails:Seq[Email],f:EmailFilter) = mails.filter(f) val sendbyOneOf:Seq[String] => EmailFilter = senders => email => senders.contains(email.sender) val notsendByAnyOf:Seq[String] => EmailFilter = senders => email => !senders.contains(email.sender) val miniMunSize:Int => EmailFilter = n => email => email.text.size >= n val maxMunSize:Int => EmailFilter = n => email => email.text.size <= n val emailFilter:EmailFilter = notsendByAnyOf(Seq("1johndoe@example.com")) //为了重用size的Email判断这一环节的code type sizeCheck = Int => Boolean val sizeConstraint:sizeCheck => EmailFilter = f => email => f(email.text.size) val minimum2Size:Int => EmailFilter = n => sizeConstraint(_ >= n) val maxmum2Size:Int => EmailFilter = n => sizeConstraint(_ <= n) def complement[A](predicate: A => Boolean) = (a: A) => !predicate(a) //由于sendbyOneOf的结果是A => Boolean,andThen使得成为andThen的参数 //也就是f andthen g 是把g应用到f的结果上 val notSentByAnyOf2 = sendbyOneOf andThen(complement(_)) //或者可以直接这样编写 val notSentByAnyOf3 = sendbyOneOf andThen(f => (x:Email) => !f(x)) val mails = Email( subject = "It's me again, your stalker friend!", text = "Hello my friend! How are you?", sender = "johndoe@example.com", recipient = "me@example.com" )::Nil //只要有一个满足条件就保留 def any[A](predicates: (A => Boolean)*): A => Boolean = a => predicates.exists(pred => pred(a)) //都不满足条件,就是对any的结果进行反转 def none[A](predicates: (A => Boolean)*) = complement(any(predicates: _*)) //全部满足条件,就是每个条件的false的反转,每个条件都false即none的结果,所以只要对每个A => Boolean结果反转,在用none求结果 def every[A](predicates: (A => Boolean)*) = none(predicates.view.map(complement(_)): _*) //Composing a transformation pipeline val addMissingSubject = (email: Email) => if (email.subject.isEmpty) email.copy(subject = "No subject") else email val checkSpelling = (email: Email) => email.copy(text = email.text.replaceAll("your", "you're")) val removeInappropriateLanguage = (email: Email) => email.copy(text = email.text.replaceAll("dynamic typing", "**CENSORED**")) val addAdvertismentToFooter = (email: Email) => email.copy(text = email.text + "\nThis mail sent via Super Awesome Free Mail") //将同参数的f进行组合 val pipeline = Function.chain(Seq( addMissingSubject, checkSpelling, removeInappropriateLanguage, addAdvertismentToFooter)) def main(args: Array[String]) { newEmailsForUser(mails,emailFilter).foreach{ x=> println(x) } } }
相关文章推荐
- const char*, char const*, char*const的区别
- Java多线程通信机制
- 编写高质量代码改善C#程序的157个建议——建议140:使用默认的访问修饰符
- RS232 RS485 通信结构
- Centos7安装cobbler2.6.9自动化部署工具
- Android UI之RadioGroup
- qDebug 学习小结
- 基于HOG特征和Neural network的人脸检测
- uvalive 2957 Bring Them There(最大流)
- ios线程-NSoperatiion
- HDU 3665 Seaside <迪杰斯特拉算法>
- 快速排序代码实现
- 黑马程序员_java基础第一部分
- Nginx反向代理配置
- Java多线程的用法详解
- node express
- 当你微信加了领导好友后,一切都变了……
- 西安 董敏之 董敏之 卡包丢失
- VS2010使整个过程说明了安装包
- C&C服务器对抗方法演进与域名产生方法(Domain generate algorithm, DGA)