类
- 一个源文件中可以包含多个类,并且都可以是public级别。
- 构造函数分为主构造函数和副构造函数,副构造函数用
def this()
声明。 - 继承extends
- 重写父类方法 override def
- 重写字段 override val , override var
//主构造器直接跟在类名后面,主构造器中的参数最后会被编译成字段
//主构造器执行时。会执行类中的所有语句
//假设参数声明时不带val和var,相当于private[this]
class Person(var name : String,val age : Int){
println("this is the primary constructor!")
var gender : String = _
val school = "ZJU"
//附属构造器名称为this
//每个附属构造器必须首先调用已经存在的主构造器,或者附属构造器
def this(name : String, age : Int, gender : String){
this(name,age)
this.gender = gender
}
}
class Student(name : String , age : Int,val major : String) extends Person(name,age){
println("this is the subclass of Person , major is : "+major)
override val school = "BJU"
override def toString = "override toString..."
}
object WeekTwo {
def main(args : Array[String]){
//val p = new Person("Jack",20,"male")
//p.name = "Jack"
//println(p.name+" : "+p.age+" : "+p.gender )
val s = new Student("Justin",20,"Math")
println(s.toString)
}
}
抽象类
- 由abstract修饰的类
- 类的一个或者多个方法没有完整的定义
- 声明抽象方法不需要加abstract关键字,只需要不写方法体
- 子类重写父类的抽象方法时不需要加override
- 父类可以声明抽象字段,即没有初始值的字段
- 子类重写父类的抽象字段时不需要加override
abstract class Person1{
def speak
val name : String
var age : Int
}
class Student1 extends Person1{
def speak {
println("speak!!!")
}
val name = "AAA"
var age = 100
}
特质trait----对比java的接口
- trait可以看作是一个可以带有具体实现的接口
- 字段和行为的集合
- 通过with关键字,一个类可以扩展多个trait
- 也可以为某个特定的对象指定trait
- trait是从左到右被构造的
trait ConsoleLogger{
def log(msg : String){
println("save money : "+msg)
}
}
trait MessageLogger extends ConsoleLogger{
override def log(msg : String){
println("save money to bank : "+msg)
}
}
abstract class Account{
def save
}
class MyAccount extends Account with ConsoleLogger{
def save{
log("100")
}
}
object Basic extends App{
val acc = new MyAccount with MessageLogger
acc.save
//save money to bank : 100
val acc2 = new MyAccount
acc2.save
//save money : 100
apply方法和单例对象
scala风格的创建对象就是定义和使用 object的apply方法,apply方法返回伴生类的对象,为什么不用构造器呢,对于嵌套表达式而言,省去new关键字会方便很多。 放在object中的所有方法可以看做是这个类的静态方法,scala没有static关键字,等效的做法是把方法定义在object里。
- 类名后面加括号调用的是object的apply方法
val a = ApplyTest()
- 对象后面加括号调用的是类的apply方法
val t = new ApplyTest
t()
class ApplyTest{
def apply() = "Apply"
def test{
println("test")
}
}
object ApplyTest{
def apply() = new ApplyTest
var count = 0
def incr = {
count = count+1
}
def static{
println("I am not a static method")
}
}
object Basic4 extends App{
// ApplyTest.static
//val a = ApplyTest()
//a.test
// val t = new ApplyTest
//println(t())
//println(t)
for (i <- 1 to 10){
ApplyTest.incr
}
println(ApplyTest.count )
}
class Person3(name : String) {
val _name = name.split("\\s+")
val firstName = _name(0)
val secondName = _name(1)
override def toString() = s"His first name is $firstName , and his second nane is $secondName."
}
object Person3{
def apply(name : String) = new Person3(name)
def main(args : Array[String]){
val a = new Person3("Xue Chao")//传统的构造方法,但不是scala风格
val b = Person3("Xue Chao")//类名后面加括号调用的是object的apply方法
println(a)
println(b)
}
}
object可以模拟static,也可以模拟单例对象,它就代表它自己。
模式匹配
- 标准用法match
- 使用守卫 _
- 匹配类型
val result = value match{
case i if i == 1 => "one"
case i if i == 2 => "two"
case _ => "some other number"
}
println("result of match is : "+result)
def t (obj : Any) = obj match{
case x : Int => println("Int")
case s : String => println("String")
case _ => println("unknown type")
}
case class(多用在模式匹配中)
- 构造器中的每个类型都为val,不建议用var。
- 不用new就可以直接产生对象,因为编译器会根据case关键字自动生成apply方法。
object CaseClassDemo extends App{
val m = Map(1->2)
m.get(10) match {
case Some(v) => println(v)
case None => println("No such key")
}
def m(p : Person){
p match {
case Teacher(_) => println("This is a teacher")
//case Teacher("Peter") => println("This is teacher Peter")
case Student(_) => println("This is a student")
case _ => println("This is unknown")
}
}
m(Student("A"))
}
abstract class Person
case class Teacher(name : String) extends Person
case class Student(name : String) extends Person
文件访问
- 按行读取 getLines()
- 按字符读取直接用文件句柄,不getLine()
- 从网络读取
import scala.io.Source
val file = Source.fromFile("D:/code/scala/week2/data.txt")
//val file = Source.fromURL("http://www.baidu.com")
for(line <- file.getLines()){
//for(line <- file){ //按字符读取
println(line)
}
option做模式匹配
option有两个子类:Some和None.如匹配到有值,为Some类型,如果没有匹配到值,返回None类型
val m = Map(1->2)
m.get(10) match {
case Some(v) => println(v)
case None => println("No such key")
}
10会输出No such key
1会输出1
String interpolation变量内插
val a = "Xuechao"
val b = "Tangbo"
println(s"$a love $b")
//输出 Xuechao love Tangbo
Comments !