Scala类的构造器与访问器

1.构造器

在Scala中,每个类都有一个主构造器。主构造器与类的定义交织在一起,如下:

class Person (
    private var _name: String, 
    private var _age: Int)

主构造器会执行类定义中的所有语句。如下,println语句是主构造器的一部分,当类被实例化时,println语句会立即执行。

class Person private(
    private var _name: String, 
    private var _age: Int){
 
    println("This class is Person")
}

通过把private修饰符添加在类参数列表的前边把主构造器隐藏起来。如:

class Person private(
    private var _name: String, 
    private var _age: Int)

这样客户代码将不能调用Person类的主构造器,如果需要设置主构造器中的参数,有两种方案:一是添加辅助构造器,二是用伴生对象的apply工厂方法。
辅助构造器
在Scala类中,有一个主构造器,但可以有任意个辅助构造器。并且,辅助构造器有两个特点:

辅助构造器的名称是this;
每个辅助构造器都必须以一个对先前已定义的其他辅助构造器或主构造器的调用开始。
辅助构造器如下定义:

def this(age: Int) = this("xx", age)

伴生对象的apply工厂方法
在存放这个类的同一个源文件中,定义它的伴生对象。伴生对象与类具有相同的访问权限,因此,即使Person类的构造器是私有的,对象Person的apply方法也可以创建新的Person对象。如:

object Person{
  def apply[T](name: String, age: Int) = new Person(name, age)
}

注意:辅助构造器只能访问主构造里定义的变量,而不能访问类里定义的变量。
2.访问器
和Java一样,Scala也有setter和getter访问器。在Scala里,对象的每个非私有的var类型成员变量都隐含定义了setter和getter方法。但是setter和getter方法的命名方式并没有沿袭Java的约定。在Scala中,var变量x的getter方法命名为“y”,setter方法命名为“y_=”(一般情况下,为了代码的可读性,y和x是一样的)。如:

class Person {
  
  private var _name: String = _
  private[this] var _age: Int = _
  //类里定义的变量,不能用构造器初始化。
  private var _address: String = _
  
  //getter
  def name: String = _name
  //setter
  def name_= (name: String): Unit = {
    _name = name
  }
  
  //getter
  def age: Int = _age
  //setter
  def age_= (age: Int): Unit = {
    _age = age
  }
}

另外,setter和getter访问器不仅可以访问类里面定义的var变量,而且还可以访问主构造器里的var变量,而且getter方法既可以访问var变量,也可以访问val变量(因为val变量不可变,所以没有setter)。如:

class Person private(
    private var _name: String,  
    private var _age: Int){
  
  //类里定义的变量,不能用构造器初始化。
  private var _address: String = _
  
  def this(age: Int) = this("xx", age) 
  
  //getter
  def name: String = _name
  //setter
  def name_= (name: String): Unit = {
    _name = name
  }
  
  //getter
  def age: Int = _age
  //setter
  def age_= (age: Int): Unit = {
    _age = age
  }
  
  //getter
  def address: String = _address
  //setter
  def address_= (address: String): Unit = {
    _address = address
  }
}

注意:getter和setter方法获取了原var变量的可见性。如var变量定义为public,则其getter和setter也是public;var变量定义为protected,则其getter和setter也是protected。

猜你喜欢

转载自www.cnblogs.com/itboys/p/10159421.html