7

Swift 2.2 (Xcode 7.3) でイライラする状況に陥っています。それをシミュレートするには、ユーザー定義の汎用クラスで変数を作成し、そのクラスを別の場所から参照します。例えば:

class A<T> {
    let genVar = 1
}

class MyViewController: UIViewController {
    let myVar = A<Int>() // crash is here
}

iOS 7 を実行しているデバイス (私の場合は iPhone 4) でこのコードを実行すると、ジェネリック型の変数を作成しようとしてクラッシュします。デバイス クラッシュ ログの最初の行は次のとおりです。

Exception Type:  EXC_BAD_ACCESS (SIGBUS)
Exception Subtype: KERN_PROTECTION_FAILURE at 0x00298910
Triggered by Thread:  0

Thread 0 Crashed:
0   libswiftCore.dylib              0x006b1d64 0x4bd000 + 2051428
1   Phone                           0x001c76ec 0xab000 + 1165036
2   libswiftCore.dylib              0x006b307c 0x4bd000 + 2056316
3   libswiftCore.dylib              0x006b2f70 0x4bd000 + 2056048
4   libswiftCore.dylib              0x006b0f24 0x4bd000 + 2047780
5   libswiftCore.dylib              0x006b107c 0x4bd000 + 2048124
6   Phone                           0x0014e730 0xab000 + 669488
7   Phone                           0x00129390 0xab000 + 517008
8   UIKit                           0x31e9d9c4 -[UIClassSwapper initWithCoder:] + 188

iOS 8 および 9 のシミュレーター/デバイスでは、上記のコードは問題なく動作します。

近い将来、iOS 7 の Swift サポートは終了しますか?

4

4 に答える 4

3

iOS 7 の Swift ジェネリックに関する 2 つのバグのように見えるものにつまずいてしまいました。修正方法は次のとおりです。

バグ #1 - クラスの最初のプロパティとしてジェネリックを定義する必要があります。

例 - このコードは失敗します:

public class TestIOS7<T> {

    private var x: Int?
}

let x = TestIOS7<String>()

しかし、回避策は次のとおりです。

public class TestIOS7<T> {

    private var kludge: T?
    private var x: Int?
}

let x = TestIOS7<String>()

バグ #2: クラスの制約が完全に壊れているようです。

例 - このコードは失敗します:

class ClassA<B: ClassB> { }

class ClassB { }

let x = ClassA <String>()

「ClassB」制約を削除し、基本的にこの言語機能が存在しないという事実に対処するためにすべてのコードを書き直す以外に、回避策は見つかりませんでした。ClassA から ClassB のイニシャライザを呼び出す必要がある場合、これは特に苦痛です。Apple がこれを修正するまで、すべての ClassB サブクラスに対してハードワイヤード if/then/else でそのブロックを書き直さなければなりませんでした。

誰かがバグ #2 の回避策を見つけたら、私に知らせてください!

于 2016-04-01T22:24:24.187 に答える
1

このバグが示唆するように、次の回避策が考えられます。

  • クラスを非ジェネリックにする
  • valueプロパティを削除
  • スワップobjectvalueプロパティの宣言
  • オブジェクトを初期化するinit

おそらく最善の回避策は、オブジェクトを初期化することですinit:

class A<T> {
    let genVar: Int
    init() {
       genVar = 1
    }

}

class MyViewController: UIViewController {
    let myVar = A<Int>() // no crash
}
于 2016-03-30T09:16:41.603 に答える
0

Xcode 7.3.1 では、ジェネリック クラスの唯一の問題は、NSObject から継承していたことです。継承を削除するだけで十分で、プロパティ宣言の順序は問題ではありませんでした。

于 2017-07-09T11:50:34.480 に答える