这有效
class Die {
let faces: Int
required init(faces: Int) {
self.faces = faces
}
func yahtzeeDice() -> [Die] {
return [Die](repeating: type(of: self).init(faces: 6), count: 5)
}
}
这似乎违反了DRY。可以在Die
函数中间接引用yahtzeeDice
答案 0 :(得分:1)
首先,请注意,问题中[Die]
数组的重复初始值设定项将实例化单个 Die
实例,然后重复对此实例的引用5次在数组中(因为Die
是引用类型)。即,您示例中的[Die]
的所有成员都对同一个基础Die
实例具有强引用。因此,如果使用引用类型,请记住避免使用重复数组初始值设定项。
现在,您可以构建一个协议,该协议提供蓝图static
骰子供应商方法的默认实现,该方法使用其他一些蓝图初始化程序提供Self
个实例数组。
// the 'class' requirement not strictly needed here, but it holds semantic
// value to explain the 'map' call rather than using array:s 'repeating'
// initializer in in the default implementation below
protocol DiceFactory: class {
init(faces: Int, id: Int)
static func dice(_ n: Int) -> [Self]
}
extension DiceFactory {
static func dice(_ n: Int) -> [Self] {
return (1...n).map { Self.init(faces: 6, id: $0) }
}
}
如果您标记了Dice
课程final
(为什么final
?请参阅下面的链接Q& A),您可以在符合时直接访问此默认实施到DiceFactory
协议。
final class Die: DiceFactory {
let id: Int
let faces: Int
init(faces: Int, id: Int) {
self.faces = faces
self.id = id
}
}
let myDice = Die.dice(5)
myDice.forEach { print($0, $0.id) }
/* Die 1
Die 2
Die 3
Die 4
Die 5 */
但是,你有充分的理由不明确地输入Die
吗?
另见: