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。

原文地址:https://www.cnblogs.com/itboys/p/10159421.html

时间: 2024-10-02 10:01:30

Scala类的构造器与访问器的相关文章

Scala类与对象

Scala类与对象 类简介 简介 类是对象的蓝图.一旦你定义了类,就可以用关键字new根据类的蓝图创建对象.在类的定义里,可以放置字段和方法,这些被笼统地称为成员.对于字段,不管是val还是var定义的,都是指向对象的变量.对于方法,用def定义,包含了可执行代码.字段保留了对象的状态或数据,而方法使用这些数据执行对象的运算工作.当类被实例化的时候,运行时环境会预留一些内存来保留对象的状态映像--即变量的内容. 示例 创建类示例: class SumAccumulator { var sum =

WorldWind源码剖析系列:地形访问器类TerrainAccessor

地形访问器类TerrainAccessor提供了对地形(高程)Terrain (elevation)访问的各种接口interface,是NltTerrainAccessor类的基类.该类类图如下. 基类TerrainAccessor提供的主要处理方法简要描述如下: protected string m_name; //地形模型名称 protected double m_north; //地形北部边界 protected double m_south; //地形南部边界 protected dou

c++第五章-(类与对象、构造器和析构器)

1.构造器与结构体的区别:构造器多支持方法.其作用有申请内存,初始化变量. 在c++中构造器没有返回值:语法Class Name(); 2.析构器的作用:释放内存. 在c++中析构器没有返回值:语法~ClassName(); class Animal { public: std::string mouth; std::string name; void eat(); void sleep(); void drool(); Animal(std::string theName); }; class

2017-9-23C#笔记(类的索引,事件,运算符,this访问器,派生,分部类,抽象类,封闭类,静态类,类与结构的不同)

1.类的索引 索引是一组get和set锋访问器,支持按照饮用数组元素的方法来引用对象.索引通常便是多个数据成员,并且它总是以雷类的事例成员的方式存在.声明索引的方法: 返回类型     this  [参数列表] { Get {    } set {        } } 例如:using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ConsoleApplicat

Scala类

要点 类中的字段自动带有getter方法和setter方法 可以用定制的getter/setter方法替换掉字段的定义,而不必修改使用类的客户端----这就是"统一访问原则" 用@BeanProperty注解来生成JavaBeans的getXxx/setXxx方法 每个类都有一个主要的构造器,这个构造器和类定义"交织"在一起.它的参数直接成为类的字段,主构造器执行类体中所有的语句. 辅助构造器是可选的,它们叫做this 在Scala源文件中,可以包含多个类,所有这些

【scala】 scala 类 (五)

1.scala类 1.class 关键字 2.var 属性 默认生成getter/setter 方法 3.val 属性 默认生成getter 方法 4. 自定义getter /setter 方法 , property 和 proeprty_ 方法来表示 getter 和setter方法 5. 主构造函数 和辅构造函数的定义使用 6.使用 @BeanProperty 来生成 getter/setter方法 7. 重写toString 方法 ,利用scala字符串插值来格式化输出 import sc

Scala 中的构造器

Scala中的构造器相较于Java比较特殊,分为两种:主构造器,从构造器.主构造器是和类中字段和方法的定义混合在一起的. 在Scala中,不需要像Java一样需要在类中定义一个与类名相同的方法来当作构造器. 主构造器的参数列表写在类名的后面,而构造器的内容,则直接写在类定义里面,所以说,一个Scala类里面,除了方法和字段的定义以外的代码,全都是主构造器的内容. class Fruit(n: String, w: Int) { val name = n val weight = w printl

使用Scala基于词法单元的解析器定制EBNF范式文法解析

一.前言 近期在做Oracle迁移到Spark平台的项目上遇到了一些平台公式翻译为SparkSQL(on Hive)的需求,而Spark采用亲妈语言Scala进行开发.分析过大概需求过后,拟使用编译原理中的EBNF范式模式,进行基于词法的文法解析.于是拟采用传统的正则词法解析到EBNF文法解析的套路来实现,直到发现了StandardTokenParsers这个Scala基于词法单元的解析器类. 二.平台公式及翻译后的SparkSQL 平台公式的样子如下所示: 1 if(XX1_m001[D003

14.C#属性访问器、命名空间、pragma指令(七章7.3-7.5)

看到一些零星的知识片,今天就用自己的理解说明下,也是因为太简单了,一下就过的,也是我们日常开发中常用.留下一个脚印,当书不在手上的,也能翻出来看看.说下属性访问器.命名空间和pragma指令. 属性访问器在01.C#数据类型.排序.过滤(一章1.1-1.2)有所提到,在C#3后可以使用修饰符去修饰属性的取值和赋值,也可以使用加入一些验证,如下: 1 class Plant 2 { 3 private double Height = 0.0; 4 5 //是否需要修剪 6 public bool