プロパティをオーバーライドしようとすると、「読み取り専用プロパティで変更可能なプロパティをオーバーライドできません」というエラーが表示されます
スーパークラスでgetおよびsetを提供しました。
class Card {
var contents:String {
get {
return self.contents
}
set {
self.contents = newValue
}
}
init() {
self.contents = ""
}
}
これが「contents」プロパティをオーバーライドしようとしている私のサブクラスです。
class PlayingCard: Card {
override var contents:String { //<-- this is where I get the build error
get {
var rankStrings:Array<String> = PlayingCard.rankStrings()
return rankStrings[Int(self.rank)] + self.suit
}
}
}
正確に私は何を間違っていますか?
オーバーライドするプロパティにゲッターとセッターの両方がある場合は、サブクラスにも両方を提供する必要があります。これが Swift言語ガイド)の関連部分 (私の強調)です:
サブクラスプロパティのオーバーライドでゲッターとセッターの両方を提供することにより、継承された読み取り専用プロパティを読み取り/書き込みプロパティとして提示できます。 ただし、継承された読み取り/書き込みプロパティを読み取り専用プロパティとして提示することはできません。
値で特別なことを何もしていない場合は、通常、設定されている値を基本クラスに渡します。
set {
super.contents = newValue
}
空のセッターを使用して値を破棄することもできます(これをオフハンドで行う正当な理由は考えられませんが)。
set { }
また、contents
クラスのCard
プロパティに無限ループがあることも指摘しておきます。あなたがこれをするとき:
get {
return self.contents
}
実際には、同じゲッターを再度呼び出して無限ループを作成しています。セッターでも同じことをしています。 Swiftは、Objective-Cが行ったようにプロパティのivarを自動的に作成しないため、自分で作成する必要があります。そのプロパティを作成するより適切な方法は、次のようなものです。
class Card {
private var _contents: String
var contents: String {
get {
return _contents
}
set {
_contents = newValue
}
}
init() {
_contents = ""
}
}
ただし、セッターとゲッターで_contents
を設定して返すこと以外は何もしていないので、次のように簡略化できます。
class Card {
var contents: String = ""
init() {
}
}
注:contents
は、オプションの(String?
)の使用にも適している可能性があります空の文字列に初期化するのではなく、nil
に設定します。
コンパイラエラーメッセージはかなり単純です。Card
のcontents
プロパティはmutableです。つまり、set
メソッドに加えてget
メソッドがあります。
オーバーライドはget
メソッドのみを追加します。set
メソッドも追加する必要があります。
私はこれがあなたが望むものだと思います:
set(newValue) {
rankStrings[Int(self.rank)] = newValue;
}