我正在通过Odersky的Scala编程第二本书学习Scala,并且刚刚介绍了讨论功能对象的第6章。在该章中,主要示例围绕创建一个类来表示有理数和有理数的算法。
他的减少课程看起来像:
class Rational (n : Int, d : Int) {
val numer : Int = n
val denom : Int = d
def add (that: Rational) : Rational =
new Rational (
numer * that.denom + that.numer * denom, denom * that.denom)
}
为了实现不变性,他引入了两个新变量numer和denom,它们表示与类参数n和d相同的概念。根据我的知识到目前为止,这意味着如果我想在Scala中创建不可变的函数对象,我总是要经历创建类参数重复的过程,这可能非常繁琐。例如,如果我想创建一个表示交易的类,我将不得不这样做:
class Trade (
direction : Char,
instrument : Instrument,
price : BigDecimal,
quantity : BigDecimal,
counterparty : Party
)
{
val direction_ = direction
val instrument_ = instrument
val price_ = price
val quantity_ = quantity
val counterparty_ = counterparty
// some great methods below...
}
我想到的唯一方法就是在上面的变量名之后添加下划线,因为我想不出方向,仪器,价格等的另一个名称。我想知道什么是最佳实践在这里,其他Scala程序员发现避免进入变量命名 - 瘫痪模式。
答案 0 :(得分:4)
如果创建注入的构造函数对象的副本的原因主要是为了能够在外部公开它们,那么您可以改写:
class Trade (
val direction : Char,
val instrument : Instrument,
val price : BigDecimal,
val quantity : BigDecimal,
val counterparty : Party)
{
// some great methods below...
}
甚至更好,用例类:http://www.scala-lang.org/old/node/107
case class Trade (
direction : Char,
instrument : Instrument,
price : BigDecimal,
quantity : BigDecimal,
counterparty : Party) {
// some great methods below...
}
答案 1 :(得分:3)
你可以像这样定义你的班级Trade
:
class Trade(val direction: Char, val instrument: Instrument, ...) // etc
换句话说,将val
放在构造函数参数的前面。不需要所有重复。
答案 2 :(得分:1)
您不必创建重复项。你可以这样做:
class Rational (val n : Int, val d : Int)
这为您的类提供了不可变字段n
和d
或者您可以使用case class
case class Rational (n : Int, d : Int)
答案 3 :(得分:0)
关于Rational
实施的附注,
case class Rational (n : Int, d : Int) {
def +(that: Rational) = Rational (n*that.d + that.n*d, d*that.d)
}
此处+
运算符重载以对Rational
进行操作。然后
val a = Rational(1,2)
val b = Rational(3,4)
val c = a+b
等等
c: Rational = Rational(10,8)