(十五)scala中的辅助构造器+scala中访问控制与方法重写

113 阅读4分钟

(一)主构造函数的参数

  • 参数修饰符的三种情况:var 和 val的区别?

1. var 是可以修改的属性

2. val 是不可以修改的属性

3.而没有使用val或者var修饰的,不是属性,不可在外部访问,不可改写。

(二)辅助构造函数

1. 构造函数(构造器)的作用是什么? 创建对象。

2. 构造函数只能有一个吗? 可以有多个。可以有很多个,其他的叫辅助构造函数。

3.辅助构造函数的作用是支持更多的创建对象的方式。

4.格式

辅助构造器的方法名固定为this,其参数不能使用var或val修饰,且必须在第一行代码中直接或间接调用主构造器

注意

  1. 主构造函数 class Student ()
  2. 辅助构造函数:提供更多的方式来创建对象
辅助构造器的作用

1.提供多种初始化方式:

辅助构造器允许类提供多种初始化选项,使得创建对象时更加灵活。

2.简化对象创建:

通过定义多个辅助构造器,您可以简化对象的创建过程,避免在主构造器中处理过多的参数。

3.调用主构造器:

辅助构造器可以通过 this 关键字调用主构造器,从而确保所有初始化逻辑都集中在主构造器中。

代码一

package level02
// class 类
// var 修饰的属性是可以被修改的
// val 修饰的属性是只读的,不能被修改
class Student(var name:String, val age:Int) {
  println("Student(van name:String, val age:Int)")

  // 辅助构造函数
  // 特点: 1. 名字就是this 2.第一行代码就是调用主构造器
  def this() = {
    this("未知", 18) // 调用主构造函数
    println("辅助构造器被调用了...")
  }

  def this(age:Int) = {
    this("未知", age)
  }
  def sayHi(): Unit = {
    println(s"我是${name}, 我今年${age}")
  }
}

object class01 {
  def main(args: Array[String]): Unit = {
    // 创建对象 = new 会自动调用构造函数
    val stu1 = new Student("小花", 18)
    val stu2 = new Student()
    val stu3 = new Student(20)
    // 调用对象的方法
    stu1.sayHi()
    // 调用对象的方法
    stu1.sayHi()
    stu2.sayHi()
    stu3.sayHi()
  }
}

代码二

package level02{

  object class06 {
    // 链式
    // arr1.map(x => 2*x).filter(x=>x>5).foreach(println)

    // 实现要点:把当前方法的返回值设置为当前对象!
    class Student() {
      def sayHi(): Student = {
        println("sayHi")
        this
      }

      def sayHello(): Student = {
        println("sayHello")
        this // 返回当前对象
      }
    }

    def main(args: Array[String]): Unit = {
      val stu1 = new Student()
      // 链式调用 方法.方法.方法......
      stu1.sayHi().sayHello()
      // val arr1 = Array(1,2,3)
      // arr1.map(x => 2*x).filter(x=>x>5).foreach(println)
    }
  }

}

(三)private

  • 默认情况下,类的属性在可以通过对象.属性名的方式来获取,如果不希望在类的外部被访问,可以用private来修饰。
  • 代码如下
package level02

object class02 {
  class Student(val name: String, val age: Int) {
    //private: 私有的。不对外公布,不对外发布,在外面不可以访问。在家之外的地方,不可以被别人知道.....
    private val hobbies: String = "躲在被子,打手电看恐怖小说"

    private def hobby(): Unit = {
      println(s"${hobbies}")
    }

    def sayHi(): Unit = {
      println(s"${name}, ${age}")

      hobby() // 在类的内部,可以调用私有方法
    }
  }

  def main(args: Array[String]): Unit = {
    val stu = new Student("小花", 18)
    stu.sayHi()
    // println(stu.hobbies)
    // stu.hobby()
  }
}

(四)判断类和对象的关系

如何知道所属类

方法1: 对象.getClass()

方法2:对象.isInstanceof[类]

package level02 {
  object class03 {
    // 判断类和对象的关系? 亲子鉴定?

    // 方式 1: 对象.getClass () // 执爹
    // 方式 2: 对象.isInstanceOf [类] // DNA 对比

    class Student() {}

    class Teacher() {}

    def main(args: Array[String]): Unit = {
      val age: Int = 1

      val stu = new Student()
      //stu 是对象名
      // Student 是类名
      //stu 是 Student 类的实例。

      // 返回类名
      println(stu.getClass) // class level02.Class03$Student
      println(age.getClass) // int
      // 注意: [ ], 结果是 Boolean 值

      println(stu.isInstanceOf[Student]) // true
      println(stu.isInstanceOf[Teacher]) // false
    }
  }
}

(五)重写toString

  • 定义toString方法
  1. 你可以在类的内部直接定义toString方法。这个方法通常不需要任何参数,并且返回一个String类型的结果。
  2. 在Scala中,要重写一个方法,你需要使用override关键字。对于toString方法,你可以在你的类中定义它,并使用override来指明这是对父类方法的重写。
  3. 代码如下
package level02

object class04 {
 // 目标:改进类的代码,让它在 println 的时候,输出的信息更友好一点!
 // 重写 toString 方法
 //(1)override 重写,覆盖....
 //(2)toString 方法,是每个对象都会自带的一个方法,当我们使用 println 时,它就会自动被调用,返回一个字符串,就是输出的内容。
  class Student(var name: String, var age: Int) {
    override def toString: String = s"姓名:${name}"
  }

  def main(args: Array[String]): Unit = {
    val stu1 = new Student("小花", 18)
    val stu2 = new Student("小明", 18)

    println(stu1) // 姓名:小花
    println(stu2) // 姓名:小明
  }
}

(六)判断两个对象是相等的?

  • 两个对象做比较==时,会自动调用equals方法。我们可以重写equals方法,并自己定义两个对象相等的标准。

  • 代码如下

package level02 {
  object class05 {
    // 目标:判断两个 Student 对象是否相等的依据是:学号相同 并且 姓名相同
    // 这里的判断条件可以自己来确定
    class Student(val id: String, val name: String, val age: Int) {
      //equals 方法
      // 在使用 == 判断的时候,会自动调用。
      // 如果返回 true,则相等
      // 如果返回是 false,则不相等
      override def equals(obj: Any): Boolean = {
        println(s"比较是否相等... ${this.id},${this.name},")
        // 在这里写自己判断逻辑
        // 把 obj 当成 Student
        val other = obj.asInstanceOf[Student]
        this.id == other.id && this.name == other.name
      }
    }

    def main(args: Array[String]): Unit = {
      val stu1 = new Student("2024101001", "小花", 18)
      val stu2 = new Student("2024101001", "小花", 19)

      if (stu1 == stu2) {
        println("他们是同一个人")
      } else {
        println("不是同一个人")
      }
      // 是指当前对象
    }
  }
}