scala学习笔记(3):类
1 类
(1)
scala把主构造函数放到类的定义中,让定义字段及相应方法变得简单起来。
class People(age: Int, name: String)
scala会自动将这个类变成public,默认的就是public. 如果我们将age这个字段设为 val age: Int,则scala将其定义成为一个private final 字段,并为它创建一个public方法number() 用以取值。如果var name: String,则定义name为private字段,并同时提供public的getter和setter方法。如果不做修饰,则设定为private的getter和setter方法。
class People{ println("Hello") }
当new People时会显示输出结果:Hello
除了主构造函数,还可以通过this()副方法构造从构造函数。Scala 里的每一个从构造器的第一个动作都是调用同一个类里面其他的构造器。换句话说 就是,每个 Scala 类里的每个从构造器都是以“this(...)”形式开头的。 这个规则的根本结果就是每一个 Scala 的构造器调用终将结束于对类的 主构造器的调用。因此主构造器是类的唯一入口点。
class People(age: Int, name: String){ private var address: String = _ def this(age: Int, name: String, add: String){ this(age,name) address = add } }
主构造器会执行类定义中的所有语句
scala> class Person(name: String, age: Int){ | println("Hi man") | def description = name + " is " + age + "years old" | println(description) | } scala> val p = new Person("a", 10) Hi man a is 10years old p: Person = Person@e7689a5
如果想让主构造器是private
scala> class Person private (name: String, age: Int){ | println("Hi man") | } defined class Person scala> val p = new Person("a", 10) <console>:11: error: constructor Person in class Person cannot be accessed in object $iw val p = new Person("a", 10)
构造器参数var, val, default
Declaration Getter? Setter? ----------- ------- ------- var yes yes val yes no default no no
// 'name' is a var class Person(var name: String) val p = new Person("Alvin Alexander") p.name // String = Alvin Alexander p.name = "Fred Flintstone" // String = Fred Flintstone // 'name' is a val class Person(val name: String) val p = new Person("Alvin Alexander") p.name // String = Alvin Alexander p.name = "Fred Flintstone" // error: reassignment to val // 'name' is neither var or val class Person(name: String) val p = new Person("Alvin Alexander") p.name // error: value name is not a member of Person // 'name' is 'private var' class Person(private var name: String) { def printName {println(name)} } val p = new Person("Alvin Alexander") p.name // error: variable name in class Person cannot be accessed in Person p.printName // Alvin Alexander
(2) 单例
单例实例对象无法初始化,所以不能给它的主构造函数传递参数。
当单例对象与某个类共享同一个名称时,他被称作是这个类的伴生对象:companion object。你必须在同一个源文件里定义类和它的伴生对象。类被称为是这个单例对象的伴生类:companion class。类和它的伴生对象可以互相访问其私有成员。
object test{ def calSum(start_index:Int, end_index:Int, call_fun: Int => Int) = { var result = 0 for (i <- start_index to end_index){ result += call_fun(i) } result } def main(args: Array[String]){ if (args.length > 0) { for (line <- Source.fromFile(args(0)).getLines) println(line.length + " " + line) } else Console.err.println("Please enter filename") } }
(3)继承
两点需要注意a) 重写父类方法需要显示override关键字,b)只有主构造函数才能往基类构造函数中传递参数
class People(age: Int, name: String){ override def toString() = { "age: "+age + " name: "+name } } class Man(age: Int, name: String, sex: String) extends People(age,name){ override def toString() = { "age: "+age + " name: "+name + " sex: "+sex } }
简单点
class People(age: Int, name: String){ override def toString = "age: "+age + " name: "+name } class Man(age: Int, name: String, sex: String) extends People(age,name){ override def toString = "age: "+age + " name: "+name + " sex: "+sex }
(4)private 字段
class Test{ private var a = 0 def set(t: Test) = t.a = 10 //通过对象访问私有字段 } class Test{ private[this] var a = 0 def set(t: Test) = t.a = 10 //不可以访问私有字段 }