一般来说,Scala 包无法做到这一点。通常,您只会在文件中本地对包进行别名:
import scala.{ math => physics }
scala> physics.min(1, 2)
res6: Int = 1
但这并不能满足您的要求。包本身不是值或类型,因此您不能这样分配它们。这些将失败:
type physics = scala.math
val physics = scala.math
使用包对象,您可以获取它的具体成员,但不能获取其中的类。例如:
scala> val physics = scala.math.`package`
physics: math.type = scala.math.package$@42fcc7e6
scala> physics.min(1, 2)
res0: Int = 1
但是使用属于传统包的对象或类型是行不通的:
scala> scala.math.BigDecimal(1)
res1: scala.math.BigDecimal = 1
scala> physics.BigDecimal(1)
<console>:13: error: value BigDecimal is not a member of object scala.math.package
physics.BigDecimal(1)
^
好的,那你应该怎么做?
您甚至考虑这样做的原因是您想隐藏您正在使用的库的实现,以便以后可以轻松替换它。如果是这种情况,您应该将库隐藏在另一个接口或对象(facade)中。这并不意味着您需要转发库中包含的每个方法和值,只需要转发您实际使用的方法和值。这样,在迁移到另一个库时,您只需要更改一个类,因为其余代码将仅引用外观。
例如,如果我们想使用 scala.math 中的 min 和 max,但后来想用另一个提供更有效解决方案的库替换它(如果存在这样的东西),我们可以创建一个像这样的外观:
object Math {
def min(x: Int, y: Int): Int = scala.math.min(x, y)
def max(x: Int, y: Int): Int = scala.math.max(x, y)
}
所有其他类将使用Math.min 和Math.max,因此当scala.math 被替换时,它们可以保持不变。您还可以将Math 设为特征(无实现)并在子类或对象中提供实现(例如ScalaMath),以便类可以注入不同的实现。