Scala 单例对象怎么定义和使用?

文章导读
Previous Quiz Next 在本章中,我们将讨论 Scala 编程中的单例对象概念。单例对象是一个类的唯一实例,无法被多次实例化。它们用于表示全局状态和实用函数。
📋 目录
  1. Scala 中的单例对象
  2. 伴生对象
  3. Singleton Objects in Practice
  4. Singleton Design Pattern
  5. Scala Singleton Object Summary
A A

Scala - 单例对象



Previous
Quiz
Next

在本章中,我们将讨论 Scala 编程中的单例对象概念。单例对象是一个类的唯一实例,无法被多次实例化。它们用于表示全局状态和实用函数。

Scala 中的单例对象

单例对象 使用 object 关键字创建,而不是 class。单例对象可以拥有在整个应用程序中共享的 method 和 value。它也可以像普通类一样扩展 class 和 trait。

语法

单例对象的语法如下 -

object SingletonName {
  // Fields and methods
}

示例

以下示例展示了 Scala 编程中的一个简单单例对象。

object Greeting {
  def sayHello(name: String): Unit = {
    println(s"Hello, $name!")
  }
}

object Demo {
  def main(args: Array[String]) = {
    Greeting.sayHello("")  // 访问单例对象的方法
  }
}

将上述程序保存为 Demo.scala。使用以下命令来编译和执行该程序。

命令

>scalac Demo.scala
>scala Demo

输出

Hello, !

在示例中,Greeting 单例对象有一个 method sayHello,用于打印问候消息。Demo 对象拥有 main 方法。它访问了 Greeting 单例对象的 sayHello 方法。

伴生对象

伴生对象 是一个与 class 共享相同名称的单例对象。伴生对象定义在同一个源文件中。伴生对象可以访问其伴生 class 的 private fields 和 methods。

语法

伴生对象的语法如下 -

class ClassName {
  // Class fields and methods
}

object ClassName {
  // Companion object fields and methods
}

示例

以下示例展示了 Scala 编程中伴生对象的使用。

class Counter {
  private var count: Int = 0

  def increment(): Unit = { count += 1 }
  def currentCount: Int = count
}

object Counter {
  def reset(counter: Counter): Unit = {
    counter.count = 0  // 访问伴生类的私有字段
  }
}

object Demo {
  def main(args: Array[String]) = {
    val counter = new Counter
    counter.increment()
    counter.increment()
    println(s"Current count: ${counter.currentCount}")  // 输出: 2
    Counter.reset(counter)
    println(s"Current count after reset: ${counter.currentCount}")  // 输出: 0
  }
}

将上述程序保存为 Demo.scala。使用以下命令来编译和执行该程序。

命令

>scalac Demo.scala
>scala Demo

输出

Current count: 2
Current count after reset: 0

在示例中,Counter class 有一个 private field count 和修改它的 methods。伴生对象 Counter 定义了一个 method reset,可以访问和修改 Counter class 的 private field count。Demo 对象使用了 Counter class 及其伴生对象。

Singleton Objects in Practice

Singleton objects 用于定义工具方法和常量、管理全局状态,以及实现 Singleton 设计模式。

Example: Utility Methods

object MathUtils {
  def add(a: Int, b: Int): Int = a + b
  def subtract(a: Int, b: Int): Int = a - b
}

object Demo {
  def main(args: Array[String]) = {
    println(s"5 + 3 = ${MathUtils.add(5, 3)}")  // 输出: 8
    println(s"5 - 3 = ${MathUtils.subtract(5, 3)}")  // 输出: 2
  }
}

将上述程序保存为 Demo.scala。以下命令用于编译和执行该程序。

Command

>scalac Demo.scala
>scala Demo

Output

5 + 3 = 8 
5 - 3 = 2

Example: Global State

object Config {
  var applicationName: String = ""
  var version: String = "1.0.0"
}

object Demo {
  def main(args: Array[String]) = {
    println(s"Application Name: ${Config.applicationName}")
    println(s"Version: ${Config.version}")

    // 修改全局状态
    Config.version = "1.1.0"
    println(s"Updated Version: ${Config.version}")
  }
}

将上述程序保存为 Demo.scala。以下命令用于编译和执行该程序。

Command

>scalac Demo.scala
>scala Demo

Output

Application Name: 
Version: 1.0.0
Updated Version: 1.1.0

Singleton Design Pattern

Singleton 设计模式确保一个 class 只有一个实例,并提供对它的全局访问点。Scala 中的 singleton objects 本质上遵循此模式。

Example

object Logger {
  def log(message: String): Unit = {
    println(s"Log: $message")
  }
}

object Demo {
  def main(args: Array[String]) = {
    Logger.log("This is a log message.")  // 访问 singleton object
  }
}

将上述程序保存为 Demo.scala。以下命令用于编译和执行该程序。

Command

>scalac Demo.scala
>scala Demo

Output

Log: This is a log message.

在示例中,Logger singleton object 有一个 log 方法,用于打印日志消息。Demo object 使用了 Logger singleton object。

Scala Singleton Object Summary

  • Singleton objects 是 class 的唯一实例。Singleton objects 不能被实例化多次。
  • Singleton objects 使用 object 关键字定义。
  • Companion objects 与 class 共享相同的名称。Singleton objects 可以访问其 companion class 的私有字段和方法。
  • Singleton objects 适用于定义工具方法、管理全局状态,以及实现 Singleton 设计模式。