scala面向对象.高阶函数,柯里化,Actor编程简介
**1.定义一个类 **
class Person{
//用val修饰的变量是只读属性,有getter但是没有setter
val id ="111"
//用var修饰的变量既有getter又有setter
var age:Int =18
//类私有字段,只能在类的内部使用,只有伴生对象内可以使用
private var name:String ="aaa"
//对象是由字段,访问权限更加严格,只有person类的方法才能访问当前对象的pet字段
private[this]val pet="bbb"
}
**2.构造器 **
每个类都有主主构造器,主构造器的参数直接放置类名后面,与类交织在一起,主构造器会执行类定义中的所有语句
class Person(val name:String){
//主构造器定义的所有语句都会执行
println("执行主构造器")
private var age=11
def this(name:String,age:Int){
//每个辅助构造器必须以主构造器或其他的辅助构造器的调用开始
this(name);
println("执行辅助构造器")
this.age = age
}
}
构造器参数可以不带var或val,如果不带val或var的参数至少被一个方法所使用,那么它将会被提升为字段
//在类名后面加private就变成了私有的
class moon private(val name:String,prop:Array[String],private var age:Int =18){
println(prop.size))
//prop被下面的方法使用,prop就变成了
def da = prop.toBuffer
}
object sun{
def main(args:Array[String]) {
//私有构造器,只能在伴生对象中使用
val q = moon("aa",Array("111","222"),20)
println(q.da())
}
}
3.单例对象
在Scala中没有静态方法和静态字段,但是可以使用object这个语法结构来达到同样的目的
1.存放工具方法和常量
2.高效共享单个不可变的实例
3.单例模式
object SingletonDemo {
def main(args: Array[String]) {
//单例对象,不需要new,用【类名.方法】调用对象中的方法
val session = SessionFactory.getSession()
println(session)
}
}
**4.伴生对象 **
在Scala的类中,与类名相同的对象叫做伴生对象,类和伴生对象之间可以相互访问私有的方法和属性
class Dog {
val id = 1
private var name = "itcast"
def printName(): Unit ={
//在Dog类中可以访问伴生对象Dog的私有属性
println( Dog.CONSTANT + name )
}
}
/**
- 伴生对象
*/
object Dog {
//伴生对象中的私有属性
private val CONSTANT = "汪汪汪 : "
def main(args: Array[String]) {
val p = new Dog
//访问私有的字段name
p.name = "123"
p.printName()
}
}
5.apply方法
通常我们会在类的伴生对象中定义apply方法,当遇到类名(参数1,...参数n)时apply方法会被调用
val arr1 = Array(5)
println(arr1.toBuffer)
调用了Array伴生对象的apply方法,arr1中只有一个元素5
6.Scala程序都必须从一个对象的main方法开始,可以通过扩展App特质,不写main方法。
7.继承一个类或实现一个接口,关键字都需要使用extends,继承后再实现需要用关键字with,
8.在Scala中重写一个非抽象的方法必须使用override修饰符
9.类型检查和转换需要使用obj.isInstanceOf[C]
10.Scala有一个十分强大的模式匹配机制,可以应用到很多场合:如switch语句、类型检查等。
并且Scala还提供了样例类,对模式匹配进行了优化,可以快速进行匹配
11.匹配模式
object CaseDemo01 extends App{
//val v = if(x >= 5) 1 else if(x < 2) 2.0 else "hello"
val arr = Array("hello", 1, 2.0, CaseDemo)
val v = arr(Random.nextInt(4))
println(v)
v match {
case x: Int => println("Int " + x)
case y: Double if(y >= 0) => println("Double "+ y)
case z: String => println("String " + z)
case _ => throw new Exception("not match exception")
}
}
匹配模式关键字使用match,case进行每种类型的匹配
case y: Double if(y >= 0) => ...
模式匹配的时候还可以添加守卫条件。如不符合守卫条件,将掉入case _中
在Scala中列表要么为空(Nil表示空列表)要么是一个head元素加上一个tail列表。
9 :: List(5, 2) :: 操作符是将给定的头和尾创建一个新的列表
注意::: 操作符是右结合的,如9 :: 5 :: 2 :: Nil相当于 9 :: (5 :: (2 :: Nil))
12.Option类型
在Scala中Option类型样例类用来表示可能存在或也可能不存在的值(Option的子类有Some和None)。Some包装了某个值,None表示没有值
def main(args: Array[String]) {
val map = Map("a" -> 1, "b" -> 2)
val v = map.get("b") match {
case Some(i) => i
case None => 0
}
**13.偏函数 **
被包在花括号内没有match的一组case语句是一个偏函数,它是PartialFunction[A, B]的一个实例,A代表参数类型,B代表返回类型,常用作输入模式匹配
def func1: PartialFunction[String, Int] = {
case "one" => 1
case "two" => 2
case _ => -1
}
14.高阶函数
定义函数时格式:val 变量名 = (输入参数类型和个数) => 函数实现和返回值类型和个数
“=”表示将函数赋给一个变量
“=>”左面表示输入参数名称、类型和个数,右边表示函数的实现和返回值类型和参数个数
15.匿名函数
在Scala中,你不需要给每一个函数命名,没有将函数赋给变量的函数叫做匿名函数
arr.map(_ *2)
其中_ *2就是一个匿名函数
16.柯里化
柯里化指的是将原来接受两个参数的方法变成新的接受一个参数的方法的过程
def m(x: Int)= (y: Int) =>xy
m: (x: Int)Int => Int
看起来比较奇怪即像方法又像函数,可以理解为一个方法的实现是 (y: Int) =>xy这个函数
调用val func = m(3)后彻底变成了一个函数
func: Int => Int =
相当于将3出入了函数中,val func =(y:Int)=>3*y
func(5)在调用这个函数并传递第二个参数,得到最终结果
Int=15
柯里化一般和隐式转换一起使用
16.隐式转换
隐式转换和隐式参数是Scala中两个非常强大的功能,利用隐式转换和隐式参数,你可以提供优雅的类库,对类库的使用者隐匿掉那些枯燥乏味的细节。
隐式转换函数是指那种以implicit关键字声明的带有单个参数的函数
/隐式的增强File类的方法
class RichFile(val from: File) {
def read = Source.fromFile(from.getPath).mkString
}
object RichFile {
//隐式转换方法
implicit def file2RichFile(from: File) = new RichFile(from)
}
object MainApp{
def main(args: Array[String]): Unit = {
//导入隐式转换
import RichFile._
//import RichFile.file2RichFile
println(new File("c://words.txt").read)
}
}
引入的隐式值>(优先级高于)默认值
如果导入的隐式值有多个同时满足参数会报错
17.泛型
多重界定符
/*
// 表示:A和B为T上界
T <: A with B
// 表示:A和B为T下界
T >: A with B
// 表示:同时拥有上界和下界,并且A为下界,B为上界,A为B的子类,顺序不能颠倒。
T >: A <: B
// 表示:类型变量界定,即同时满足AT这种隐式值和BT这种隐式值
T:A:B
// 表示:视图界定,即同时能够满足隐式转换的A和隐式转换的B
T <% A <% B
*/
具体泛型使用可见:
http://blog.csdn.net/yuan_xw/article/details/49363749
18.Actor编程
Scala中的Actor能够实现并行编程的强大功能,它是基于事件模型的并发机制,Scala是运用消息(message)的发送、接收来实现多线程的。使用Scala能够更容易地实现多线程应用的开发。
在Scala中,我们可以通过复制不可变状态的资源(即对象,Scala中一切都是对象,连函数、方法也是)的一个副本,再基于Actor的消息发送、接收机制进行并行编程
19.Actor方法执行顺序
(1).首先调用start()方法启动Actor
(2).调用start()方法后其act()方法会被执行
(3).向Actor发送消息
20.发送消息的方式
! 发送异步消息,没有返回值。
!? 发送同步消息,等待返回值。
!! 发送异步消息,返回值是 Future[Any]。
21.
class AppleActor extends Actor {
def act(): Unit = {
while (true) {
receive {
case "start" => println("starting ...")
case SyncMsg(id, msg) => {
println(id + ",sync " + msg)
Thread.sleep(5000)
sender ! ReplyMsg(3,"finished")
}
case AsyncMsg(id, msg) => {
println(id + ",async " + msg)
Thread.sleep(5000)
}
}
}
}
}
object AppleActor {
def main(args: Array[String]) {
val a = new AppleActor
a.start()
//异步消息
a ! AsyncMsg(1, "hello actor")
println("异步消息发送完成")
//同步消息
//val content = a.!?(1000, SyncMsg(2, "hello actor"))
//println(content)
val reply = a !! SyncMsg(2, "hello actor")
println(reply.isSet)
//println("123")
val c = reply.apply()
println(reply.isSet)
println(c)
}
}
case class SyncMsg(id : Int, msg: String)
case class AsyncMsg(id : Int, msg: String)
case class ReplyMsg(id : Int, msg: String)
receive阻塞(内部阻塞队列),接受消息,
sender 拿到消息的发送者
isSet判断val中有没有值
apply()方法是同步的
react方法复用线程
while(true)和loop的效果一样的
22.
读取文件内容source.fromFile(f)
f为文件内容
scala面向对象.高阶函数,柯里化,Actor编程简介的更多相关文章
- 高阶函数,柯里化,sort排序
高阶函数概念 first class object: 函数在python中时一等公民. 函数也是对象,可调用的对象. 函数可以作为普通变量,参数,返回值等等. 高阶函数: ...
- js高阶函数应用—函数柯里化和反柯里化
在Lambda演算(一套数理逻辑的形式系统,具体我也没深入研究过)中有个小技巧:假如一个函数只能收一个参数,那么这个函数怎么实现加法呢,因为高阶函数是可以当参数传递和返回值的,所以问题就简化为:写一个 ...
- Python高阶函数及函数柯里化
1 Python高阶函数 接收函数为参数,或者把函数作为结果返回的函数为高阶函数. 1.1 自定义sort函数 要求:仿照内建函数sorted,自行实现一个sort函数.内建函数sorted函数是返回 ...
- 从 ES6 高阶箭头函数理解函数柯里化
前言:第一次看到多个连续箭头函数是在一个 react 项目中,然鹅确认了下眼神,并不是对的人,因为看得一脸懵逼.em......于是开始各种搜索,先是知道了多个连续箭头函数就是 es6 的多次柯里化的 ...
- js高阶函数应用—函数柯里化和反柯里化(二)
第上一篇文章中我们介绍了函数柯里化,顺带提到了偏函数,接下来我们继续话题,进入今天的主题-函数的反柯里化. 在上一篇文章中柯里化函数你可能需要去敲许多代码,理解很多代码逻辑,不过这一节我们讨论的反科里 ...
- Scala 基础(十二):Scala 函数式编程(四)高级(二)参数(类型)推断、闭包(closure)、函数柯里化(curry)、控制抽象
1 参数(类型)推断 参数推断省去类型信息(在某些情况下[需要有应用场景],参数类型是可以推断出来的,如list=(1,2,3) list.map() map中函数参数类型是可以推断的),同时也可以 ...
- React-高阶函数_函数柯里化
高阶函数_函数柯里化 高阶函数(定义) 如果一个函数符合下面两个规范,就是高阶函数: 如果A函数,接收的参数是一个函数,那么A就是一个高阶函数(比如数组方法arr.map()接收的就是一个处理item ...
- 函数柯里化(Currying)示例
”函数柯里化”是指将多变量函数拆解为单变量的多个函数的依次调用, 可以从高元函数动态地生成批量的低元的函数.可以看成一个强大的函数工厂,结合函数式编程,可以叠加出很BT的能力.下面给出了两个示例,说明 ...
- JavaScript函数柯里化的一些思考
1. 高阶函数的坑 在学习柯里化之前,我们首先来看下面一段代码: var f1 = function(x){ return f(x); }; f1(x); 很多同学都能看出来,这些写是非常傻的,因为函 ...
随机推荐
- js返回值 数组去重
function myfun(arr){ var arr1 = new Array(); var len = arr.length; ;i <len ;i++){ ) { arr1.push(a ...
- javaIO缓冲区
java中IO类分类. 图来自网络 缓冲区:应用程序在内存中开辟的一个空间.用来放置需要被写入或写出的数据. 使用缓冲区的 优点:使得应用程序操作磁盘(或者说是与磁盘的通信)的次数降低,提高应用程序的 ...
- delphi中怎么获取服务器的时间
下面是公司的代码,调整成ADO控件,给你参考一下: function GetNetDate: TDateTime; begin with TADOQuery.Create(nil) do begin ...
- 如何禁止复制电脑文件到U盘、禁止U盘拷贝文件
在公司局域网中,有时候我们处于保护电脑文件安全和商业机密的需要,会禁止局域网电脑使用U盘.禁用USB存储设备:或者禁止通过U盘复制电脑文件.禁止U盘拷贝公司电脑文件.那么,怎样实现呢?本文提供两种方法 ...
- 无需破解:Windows Server 2008 R2 至少免费使用 900天
无需破解:Windows Server 2008 R2 至少免费使用 900天 2009年10月30日 星期五 02:10 1.首先安装后,有一个180天的试用期. 2.在180天试用期即将结束时,使 ...
- Gulp实现静态网页模块化的方法详解
前言: 在做纯静态页面开发的过程中,难免会遇到一些的尴尬问题.比如:整套代码有50个页面,其中有40个页面顶部和底部模块相同.那么同样的两段代码我们复制了40遍(最难受的方法).然后,这个问题就这样解 ...
- python---random模块详解
在python中用于生成随机数的模块是random,在使用前需要import, 下面看下它的用法. random.random random.random()用于生成一个0到1的随机符点数: 0 &l ...
- asp.net 的三种开发模式
一, Web Pages 是三种创建 ASP.NET 网站和 Web 应用程序的编程模式中的一种. 其他两种编程模式是 Web Forms 和 MVC(Model View Controller 模型 ...
- 数字对——RMQ+二分答案
题目描述 小H是个善于思考的学生,现在她又在思考一个有关序列的问题. 她的面前浮现出一个长度为n的序列{ai},她想找出一段区间[L, R](1 <= L <= R <= n). 这 ...
- Web项目替换jar包中的文件的方法
经常遇到这样的问题,需要修改jar包中的方法.应该如何做? 1.有些很人性化的框架jar包,比如SpringSecurity,可以修改配置文件指定一个新建的类,让类实现Jar包中的对应的接口就好了. ...